Made sanity checks when setting reparse data of known type
parent
2f8ced2ddd
commit
b842a6720e
|
@ -393,6 +393,62 @@ static int ntfs_drive_letter(ntfs_volume *vol, ntfschar letter)
|
|||
return (ret);
|
||||
}
|
||||
|
||||
/*
|
||||
* Do some sanity checks on reparse data
|
||||
*
|
||||
* The only general check is about the size (at least the tag must
|
||||
* be present)
|
||||
* If the reparse data looks like a junction point or symbolic
|
||||
* link, more checks can be done.
|
||||
*
|
||||
*/
|
||||
|
||||
static BOOL valid_reparse_data(ntfs_inode *ni,
|
||||
const REPARSE_POINT *reparse_attr, size_t size)
|
||||
{
|
||||
BOOL ok;
|
||||
unsigned int offs;
|
||||
unsigned int lth;
|
||||
const struct MOUNT_POINT_REPARSE_DATA *mount_point_data;
|
||||
const struct SYMLINK_REPARSE_DATA *symlink_data;
|
||||
|
||||
ok = ni && reparse_attr
|
||||
&& (size >= sizeof(REPARSE_POINT))
|
||||
&& (((size_t)le16_to_cpu(reparse_attr->reparse_data_length)
|
||||
+ sizeof(REPARSE_POINT)) == size);
|
||||
if (ok) {
|
||||
switch (reparse_attr->reparse_tag) {
|
||||
case IO_REPARSE_TAG_MOUNT_POINT :
|
||||
mount_point_data = (const struct MOUNT_POINT_REPARSE_DATA*)
|
||||
reparse_attr->reparse_data;
|
||||
offs = le16_to_cpu(mount_point_data->subst_name_offset);
|
||||
lth = le16_to_cpu(mount_point_data->subst_name_length);
|
||||
/* consistency checks */
|
||||
if (!(ni->mrec->flags & MFT_RECORD_IS_DIRECTORY)
|
||||
|| ((size_t)((sizeof(REPARSE_POINT)
|
||||
+ sizeof(struct MOUNT_POINT_REPARSE_DATA)
|
||||
+ offs + lth)) > size))
|
||||
ok = FALSE;
|
||||
break;
|
||||
case IO_REPARSE_TAG_SYMLINK :
|
||||
symlink_data = (const struct SYMLINK_REPARSE_DATA*)
|
||||
reparse_attr->reparse_data;
|
||||
offs = le16_to_cpu(symlink_data->subst_name_offset);
|
||||
lth = le16_to_cpu(symlink_data->subst_name_length);
|
||||
if ((size_t)((sizeof(REPARSE_POINT)
|
||||
+ sizeof(struct SYMLINK_REPARSE_DATA)
|
||||
+ offs + lth)) > size)
|
||||
ok = FALSE;
|
||||
break;
|
||||
default :
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (!ok)
|
||||
errno = EINVAL;
|
||||
return (ok);
|
||||
}
|
||||
|
||||
/*
|
||||
* Check and translate the target of a junction point or
|
||||
* a full absolute symbolic link.
|
||||
|
@ -654,7 +710,8 @@ char *ntfs_make_symlink(ntfs_inode *ni, const char *mnt_point,
|
|||
vol = ni->vol;
|
||||
reparse_attr = (REPARSE_POINT*)ntfs_attr_readall(ni,
|
||||
AT_REPARSE_POINT,(ntfschar*)NULL, 0, &attr_size);
|
||||
if (reparse_attr && attr_size) {
|
||||
if (reparse_attr && attr_size
|
||||
&& valid_reparse_data(ni, reparse_attr, attr_size)) {
|
||||
switch (reparse_attr->reparse_tag) {
|
||||
case IO_REPARSE_TAG_MOUNT_POINT :
|
||||
mount_point_data = (struct MOUNT_POINT_REPARSE_DATA*)
|
||||
|
@ -1016,7 +1073,7 @@ int ntfs_set_ntfs_reparse_data(const char *path __attribute__((unused)),
|
|||
ntfs_index_context *xr;
|
||||
|
||||
res = 0;
|
||||
if (ni && value && (size >= 4)) {
|
||||
if (ni && valid_reparse_data(ni, (const REPARSE_POINT*)value, size)) {
|
||||
xr = open_reparse_index(ni->vol);
|
||||
if (xr) {
|
||||
if (!ntfs_attr_exist(ni,AT_REPARSE_POINT,
|
||||
|
|
Loading…
Reference in New Issue