smb_fsinfo.c revision 9fb67ea305c66b6a297583b9b0db6796b0dfe497
/*
* CDDL HEADER START
*
* The contents of this file are subject to the terms of the
* Common Development and Distribution License (the "License").
* You may not use this file except in compliance with the License.
*
* You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
* See the License for the specific language governing permissions
* and limitations under the License.
*
* When distributing Covered Code, include this CDDL HEADER in each
* file and include the License file at usr/src/OPENSOLARIS.LICENSE.
* If applicable, add the following below this CDDL HEADER, with the
* fields enclosed by brackets "[]" replaced with your own identifying
* information: Portions Copyright [yyyy] [name of copyright owner]
*
* CDDL HEADER END
*/
/*
* Copyright 2010 Sun Microsystems, Inc. All rights reserved.
* Use is subject to license terms.
*/
#include <smbsrv/smb_kproto.h>
#include <smbsrv/smb_fsops.h>
/*
* smb_fssize_t
* volume_units and volume avail are the total allocated and
* available units on the volume.
* caller_units and caller_avail are the allocated and available
* units on the volume for the user associated with the calling
* thread.
*/
typedef struct smb_fssize {
} smb_fssize_t;
/*
* File System Control Flags for smb_com_trans2_query|set_fs_information
* level SMB_FILE_FS_CONTROL_INFORMATION
*/
#define FILE_VC_QUOTA_TRACK 0x00000001
#define FILE_VC_QUOTA_ENFORCE 0x00000002
#define FILE_VC_CONTENT_INDEX_DISABLED 0x00000008
#define FILE_VC_LOG_QUOTA_THRESHOLD 0x00000010
#define FILE_VC_LOG_QUOTA_LIMIT 0x00000020
#define FILE_VC_LOG_VOLUME_THRESHOLD 0x00000040
#define FILE_VC_LOG_VOLUME_LIMIT 0x00000080
#define FILE_VC_QUOTAS_INCOMPLETE 0x00000100
#define FILE_VC_QUOTAS_REBUILDING 0x00000200
/*
* smb_com_query_information_disk
*
* The SMB_COM_QUERY_INFORMATION_DISK command is used to determine the
* capacity and remaining free space on the drive hosting the directory
* structure indicated by Tid in the SMB header.
*
* The blocking/allocation units used in this response may be independent
* of the actual physical or logical blocking/allocation algorithm(s) used
* internally by the server. However, they must accurately reflect the
* amount of space on the server.
*
* This SMB only returns 16 bits of information for each field, which may
* not be large enough for some disk systems. In particular TotalUnits is
* commonly > 64K. Fortunately, it turns out the all the client cares
* about is the total disk size, in bytes, and the free space, in bytes.
* So, it is reasonable for a server to adjust the relative values of
* BlocksPerUnit and BlockSize to accommodate. If after all adjustment,
* the numbers are still too high, the largest possible values for
* TotalUnit or FreeUnits (i.e. 0xFFFF) should be returned.
*/
{
return (SDRC_SUCCESS);
}
void
{
}
{
int rc;
unsigned long block_size, unit_size;
unsigned short blocks_per_unit, bytes_per_block;
unsigned short total_units, free_units;
return (SDRC_ERROR);
}
return (SDRC_ERROR);
/*
* It seems that DOS clients cannot handle block sizes
* bigger than 512 KB. So we have to set the block size at
* most to 512
*/
while (block_size > 512) {
block_size >>= 1;
unit_size <<= 1;
}
/* adjust blocks and sizes until they fit into a word */
while (total_blocks >= 0xFFFF) {
total_blocks >>= 1;
free_blocks >>= 1;
unit_size >>= 1;
total_blocks = 0xFFFF;
free_blocks <<= 1;
break;
}
}
0xFFFF : (unsigned short)total_blocks;
0xFFFF : (unsigned short)free_blocks;
bytes_per_block = (unsigned short)block_size;
blocks_per_unit = (unsigned short)unit_size;
5,
total_units, /* total_units */
blocks_per_unit, /* blocks_per_unit */
bytes_per_block, /* blocksize */
free_units, /* free_units */
0); /* bcc */
}
/*
* smb_com_trans2_query_fs_information
*
* This transaction requests information about the filesystem.
* The following information levels are supported:
*
* InformationLevel Value
* ================================== ======
* SMB_INFO_ALLOCATION 1
* SMB_INFO_VOLUME 2
* SMB_QUERY_FS_VOLUME_INFO 0x102
* SMB_QUERY_FS_SIZE_INFO 0x103
* SMB_QUERY_FS_DEVICE_INFO 0x104
* SMB_QUERY_FS_ATTRIBUTE_INFO 0x105
* SMB_FILE_FS_VOLUME_INFORMATION 1001
* SMB_FILE_FS_SIZE_INFORMATION 1003
* SMB_FILE_FS_DEVICE_INFORMATION 1004
* SMB_FILE_FS_ATTRIBUTE_INFORMATION 1005
* SMB_FILE_FS_CONTROL_INFORMATION 1006
* SMB_FILE_FS_FULLSIZE_INFORMATION 1007
*
* The fsid provides a system-wide unique file system ID.
* fsid.val[0] is the 32-bit dev for the file system of the share root
* smb_node.
* fsid.val[1] is the file system type.
*/
{
char *encode_str, *tmpbuf;
char *fsname = "NTFS";
return (SDRC_ERROR);
}
return (SDRC_ERROR);
switch (infolev) {
case SMB_INFO_ALLOCATION:
return (SDRC_ERROR);
0,
break;
case SMB_INFO_VOLUME:
/*
* In this response, the unicode volume label is NOT
* expected to be aligned. Encode ('U') into a temporary
* buffer, then encode buffer as a byte stream ('#c').
*/
if (rc >= 0) {
}
} else {
}
if (rc < 0)
return (SDRC_ERROR);
break;
case SMB_QUERY_FS_VOLUME_INFO:
encode_str = "%qllb.U";
} else {
encode_str = "%qllb.s";
}
/*
* NT has the "supports objects" flag set to 1.
*/
0ll, /* Volume creation time */
length, /* label length */
0, /* Supports objects */
break;
case SMB_QUERY_FS_SIZE_INFO:
return (SDRC_ERROR);
break;
case SMB_QUERY_FS_DEVICE_INFO:
break;
encode_str = "%lllU";
} else {
encode_str = "%llls";
}
MAXNAMELEN, /* max name */
length, /* label length */
fsname);
break;
return (SDRC_ERROR);
}
0, /* free space start filtering - MUST be 0 */
0, /* free space threshold - MUST be 0 */
0, /* free space stop filtering - MUST be 0 */
SMB_QUOTA_UNLIMITED, /* default quota threshold */
SMB_QUOTA_UNLIMITED, /* default quota limit */
FILE_VC_QUOTA_ENFORCE, /* fs control flag */
0); /* pad bytes */
break;
return (SDRC_ERROR);
break;
return (SDRC_ERROR);
default:
return (SDRC_ERROR);
}
return (SDRC_SUCCESS);
}
/*
* smb_fssize
*
* File system size information, for the volume and for the user
* initiating the request.
*
* If there's no quota entry for the user initiating the request,
* caller_units and caller_avail are the total and available units
* for the volume (volume_units, volume_avail).
* If there is a quota entry for the user initiating the request,
* and it is not SMB_QUOTA_UNLIMITED, calculate caller_units and
* caller_avail as follows:
* caller_units = quota limit / bytes_per_unit
* caller_avail = remaining quota / bytes_per_unit
*
* A quota limit of SMB_QUOTA_UNLIMITED means that the user's quota
* is specfied as unlimited. A quota limit of 0 means there is no
* quota specified for the user.
*
* Returns: 0 - success
* -1 - error. Error status set in sr.
*/
static int
{
int rc, bytes_per_unit;
return (-1);
}
return (0);
return (0);
fssize->fs_caller_avail = 0;
else
}
return (0);
}
/*
* smb_com_trans2_set_fs_information
*
* This transaction sets filesystem information.
* The following information levels are supported:
*
* InformationLevel Value
* ================================== ======
* SMB_FILE_FS_CONTROL_INFORMATION 1006
*/
{
return (SDRC_ERROR);
}
return (SDRC_ERROR);
switch (infolev) {
return (SDRC_ERROR);
break;
return (SDRC_ERROR);
default:
return (SDRC_ERROR);
}
return (SDRC_SUCCESS);
}
/*
* smb_trans2_set_fs_ctrl_info
*
* Only users with Admin privileges (i.e. of the BUILTIN/Administrators
* group) will be allowed to set quotas.
*
* Currently QUOTAS are always ENFORCED and the default values
* are always SMB_QUOTA_UNLIMITED (none). Any attempt to set
* values other than these will result in NT_STATUS_NOT_SUPPORTED.
*/
static int
{
int rc;
return (-1);
}
return (-1);
}
return (-1);
}
/* Only support ENFORCED quotas with UNLIMITED default */
if ((qctrl != FILE_VC_QUOTA_ENFORCE) ||
(qlimit != SMB_QUOTA_UNLIMITED) ||
(qthresh != SMB_QUOTA_UNLIMITED)) {
return (-1);
}
return (0);
}