X-Git-Url: http://www.aleph1.co.uk/gitweb/?p=yaffs2.git;a=blobdiff_plain;f=direct%2Fyaffsfs.c;h=f32808d758829d4893a175f753a7a6fd01ea727f;hp=3745f6189011c60bd14e63b9184c8212f9b36351;hb=7b53d290e92e619a315399ba49aadf6b40e13660;hpb=a6b656e2ec808ffab1b5f46babcdc5f7b49b7a46 diff --git a/direct/yaffsfs.c b/direct/yaffsfs.c index 3745f61..f32808d 100644 --- a/direct/yaffsfs.c +++ b/direct/yaffsfs.c @@ -211,8 +211,10 @@ static void yaffsfs_PutInode(int inodeId) if(inodeId >= 0 && inodeId < YAFFSFS_N_HANDLES){ yaffsfs_Inode *in = & yaffsfs_inode[inodeId]; in->count--; - if(in->count <= 0) + if(in->count <= 0){ yaffsfs_ReleaseInode(in); + in->count = 0; + } } } @@ -277,15 +279,19 @@ static int yaffsfs_PutHandle(int handle) return 0; } -static void yaffsfs_PutDeviceHandles(struct yaffs_dev *dev) +static void yaffsfs_BreakDeviceHandles(struct yaffs_dev *dev) { - yaffsfs_Handle *yh; + yaffsfs_Handle *h; + struct yaffs_obj *obj; int i; for(i = 0; i < YAFFSFS_N_HANDLES; i++){ - yh = & yaffsfs_handle[i]; - if(yh->useCount>0 && - yaffsfs_inode[yh->inodeId].iObj->my_dev == dev) - yaffsfs_PutHandle(i); + h = yaffsfs_GetHandlePointer(i); + obj = yaffsfs_GetHandleObject(i); + if(h && h->useCount>0 && obj && obj->my_dev == dev){ + h->useCount = 0; + yaffsfs_PutInode(h->inodeId); + h->inodeId = -1; + } } } @@ -413,6 +419,22 @@ static struct yaffs_dev *yaffsfs_FindDevice(const YCHAR *path, YCHAR **restOfPat return retval; } +static int yaffsfs_CheckPath(const YCHAR *path) +{ + int n=0; + int divs=0; + while(*path && n < YAFFS_MAX_NAME_LENGTH && divs < 100){ + if(yaffsfs_IsPathDivider(*path)){ + n=0; + divs++; + } else + n++; + path++; + } + + return (*path) ? -1 : 0; +} + /* FindMountPoint only returns a dev entry if the path is a mount point */ static struct yaffs_dev *yaffsfs_FindMountPoint(const YCHAR *path) { @@ -609,6 +631,11 @@ int yaffs_open_sharing(const YCHAR *path, int oflag, int mode, int sharing) u8 readRequested; u8 writeRequested; + if(yaffsfs_CheckPath(path) < 0){ + yaffsfs_SetError(-ENAMETOOLONG); + return -1; + } + /* O_EXCL only has meaning if O_CREAT is specified */ if(!(oflag & O_CREAT)) oflag &= ~(O_EXCL); @@ -860,6 +887,7 @@ int yaffsfs_do_read(int fd, void *vbuf, unsigned int nbyte, int isPread, int off struct yaffs_obj *obj = NULL; int pos = 0; int startPos = 0; + int endPos = 0; int nRead = 0; int nToRead = 0; int totalRead = 0; @@ -878,6 +906,9 @@ int yaffsfs_do_read(int fd, void *vbuf, unsigned int nbyte, int isPread, int off /* Not a reading handle */ yaffsfs_SetError(-EINVAL); totalRead = -1; + } else if(nbyte > YAFFS_MAX_FILE_SIZE){ + yaffsfs_SetError(-EINVAL); + totalRead = -1; } else { if(isPread) startPos = offset; @@ -897,6 +928,15 @@ int yaffsfs_do_read(int fd, void *vbuf, unsigned int nbyte, int isPread, int off yaffsfs_GetHandle(fd); + endPos = pos + nbyte; + + if(pos < 0 || pos > YAFFS_MAX_FILE_SIZE || + nbyte > YAFFS_MAX_FILE_SIZE || + endPos < 0 || endPos > YAFFS_MAX_FILE_SIZE){ + totalRead = -1; + nbyte = 0; + } + while(nbyte > 0) { nToRead = YAFFSFS_RW_SIZE - (pos & (YAFFSFS_RW_SIZE -1)); if(nToRead > nbyte) @@ -936,9 +976,8 @@ int yaffsfs_do_read(int fd, void *vbuf, unsigned int nbyte, int isPread, int off if(!isPread) { if(totalRead >= 0) h->position = startPos + totalRead; - else { - /* todo error */ - } + else + yaffsfs_SetError(-EINVAL); } } @@ -965,6 +1004,7 @@ int yaffsfs_do_write(int fd, const void *vbuf, unsigned int nbyte, int isPwrite, struct yaffs_obj *obj = NULL; int pos = 0; int startPos = 0; + int endPos; int nWritten = 0; int totalWritten = 0; int write_trhrough = 0; @@ -992,6 +1032,15 @@ int yaffsfs_do_write(int fd, const void *vbuf, unsigned int nbyte, int isPwrite, yaffsfs_GetHandle(fd); pos = startPos; + endPos = pos + nbyte; + + if(pos < 0 || pos > YAFFS_MAX_FILE_SIZE || + nbyte > YAFFS_MAX_FILE_SIZE || + endPos < 0 || endPos > YAFFS_MAX_FILE_SIZE){ + totalWritten = -1; + nbyte = 0; + } + while(nbyte > 0) { nToWrite = YAFFSFS_RW_SIZE - (pos & (YAFFSFS_RW_SIZE -1)); @@ -1035,9 +1084,8 @@ int yaffsfs_do_write(int fd, const void *vbuf, unsigned int nbyte, int isPwrite, if(!isPwrite){ if(totalWritten > 0) h->position = startPos + totalWritten; - else { - /* todo error */ - } + else + yaffsfs_SetError(-EINVAL); } } @@ -1063,6 +1111,11 @@ int yaffs_truncate(const YCHAR *path,off_t new_size) struct yaffs_obj *dir = NULL; int result = YAFFS_FAIL; + if(yaffsfs_CheckPath(path) < 0){ + yaffsfs_SetError(-ENAMETOOLONG); + return -1; + } + yaffsfs_Lock(); obj = yaffsfs_FindObject(NULL,path,0,1,&dir); @@ -1122,10 +1175,11 @@ off_t yaffs_lseek(int fd, off_t offset, int whence) h = yaffsfs_GetHandlePointer(fd); obj = yaffsfs_GetHandleObject(fd); - if(!h || !obj){ - /* bad handle */ + if(!h || !obj) yaffsfs_SetError(-EBADF); - } else { + else if(offset > YAFFS_MAX_FILE_SIZE) + yaffsfs_SetError(-EINVAL); + else { if(whence == SEEK_SET){ if(offset >= 0) pos = offset; @@ -1138,10 +1192,12 @@ off_t yaffs_lseek(int fd, off_t offset, int whence) pos = fSize + offset; } - if(pos >= 0) + if(pos >= 0 && pos <= YAFFS_MAX_FILE_SIZE) h->position = pos; - else + else{ yaffsfs_SetError(-EINVAL); + pos = -1; + } } yaffsfs_Unlock(); @@ -1157,6 +1213,11 @@ int yaffsfs_DoUnlink(const YCHAR *path,int isDirectory) YCHAR *name; int result = YAFFS_FAIL; + if(yaffsfs_CheckPath(path) < 0){ + yaffsfs_SetError(-ENAMETOOLONG); + return -1; + } + yaffsfs_Lock(); obj = yaffsfs_FindObject(NULL,path,0,0,NULL); @@ -1204,6 +1265,11 @@ int yaffs_rename(const YCHAR *oldPath, const YCHAR *newPath) yaffsfs_Lock(); + if(yaffsfs_CheckPath(newPath) < 0){ + yaffsfs_SetError(-ENAMETOOLONG); + return -1; + } + olddir = yaffsfs_FindDirectory(NULL,oldPath,&oldname,0); newdir = yaffsfs_FindDirectory(NULL,newPath,&newname,0); obj = yaffsfs_FindObject(NULL,oldPath,0,0,NULL); @@ -1297,6 +1363,11 @@ static int yaffsfs_DoStatOrLStat(const YCHAR *path, struct yaffs_stat *buf,int d int retVal = -1; + if(yaffsfs_CheckPath(path) < 0){ + yaffsfs_SetError(-ENAMETOOLONG); + return -1; + } + yaffsfs_Lock(); obj = yaffsfs_FindObject(NULL,path,0,1,&dir); @@ -1358,6 +1429,11 @@ static int yaffs_do_setxattr(const YCHAR *path, const char *name, const void *da int retVal = -1; + if(yaffsfs_CheckPath(path) < 0){ + yaffsfs_SetError(-ENAMETOOLONG); + return -1; + } + yaffsfs_Lock(); obj = yaffsfs_FindObject(NULL,path,0,1,&dir); @@ -1426,6 +1502,11 @@ static int yaffs_do_getxattr(const YCHAR *path, const char *name, void *data, in int retVal = -1; + if(yaffsfs_CheckPath(path) < 0){ + yaffsfs_SetError(-ENAMETOOLONG); + return -1; + } + yaffsfs_Lock(); obj = yaffsfs_FindObject(NULL,path,0,1,&dir); @@ -1492,6 +1573,11 @@ static int yaffs_do_listxattr(const YCHAR *path, char *data, int size, int follo int retVal = -1; + if(yaffsfs_CheckPath(path) < 0){ + yaffsfs_SetError(-ENAMETOOLONG); + return -1; + } + yaffsfs_Lock(); obj = yaffsfs_FindObject(NULL,path,0,1,&dir); @@ -1558,6 +1644,11 @@ static int yaffs_do_removexattr(const YCHAR *path, const char *name, int follow) int retVal = -1; + if(yaffsfs_CheckPath(path) < 0){ + yaffsfs_SetError(-ENAMETOOLONG); + return -1; + } + yaffsfs_Lock(); obj = yaffsfs_FindObject(NULL,path,0,1, &dir); @@ -1721,6 +1812,11 @@ int yaffs_access(const YCHAR *path, int amode) int retval = -1; + if(yaffsfs_CheckPath(path) < 0){ + yaffsfs_SetError(-ENAMETOOLONG); + return -1; + } + if(amode & ~(R_OK | W_OK | X_OK)){ yaffsfs_SetError(-EINVAL); return -1; @@ -1763,6 +1859,11 @@ int yaffs_chmod(const YCHAR *path, mode_t mode) struct yaffs_obj *dir=NULL; int retVal = -1; + if(yaffsfs_CheckPath(path) < 0){ + yaffsfs_SetError(-ENAMETOOLONG); + return -1; + } + if(mode & ~(0777)){ yaffsfs_SetError(-EINVAL); return -1; @@ -1856,6 +1957,11 @@ int yaffs_mkdir(const YCHAR *path, mode_t mode) YCHAR *alt_path = NULL; int retVal= -1; + if(yaffsfs_CheckPath(path) < 0){ + yaffsfs_SetError(-ENAMETOOLONG); + return -1; + } + if(yaffsfs_alt_dir_path(path, &alt_path) < 0){ yaffsfs_SetError(-ENOMEM); return -1; @@ -1895,6 +2001,11 @@ int yaffs_rmdir(const YCHAR *path) int result; YCHAR *alt_path; + if(yaffsfs_CheckPath(path) < 0){ + yaffsfs_SetError(-ENAMETOOLONG); + return -1; + } + if(yaffsfs_alt_dir_path(path, &alt_path) < 0){ yaffsfs_SetError(-ENOMEM); return -1; @@ -1924,6 +2035,11 @@ int yaffs_mount2(const YCHAR *path,int read_only) T(YAFFS_TRACE_MOUNT,(TSTR("yaffs: Mounting %s" TENDSTR),path)); + if(yaffsfs_CheckPath(path) < 0){ + yaffsfs_SetError(-ENAMETOOLONG); + return -1; + } + yaffsfs_Lock(); yaffsfs_InitHandles(); @@ -1961,6 +2077,11 @@ int yaffs_sync(const YCHAR *path) int retVal=-1; struct yaffs_dev *dev=NULL; YCHAR *dummy; + + if(yaffsfs_CheckPath(path) < 0){ + yaffsfs_SetError(-ENAMETOOLONG); + return -1; + } yaffsfs_Lock(); dev = yaffsfs_FindDevice(path,&dummy); @@ -1990,6 +2111,11 @@ int yaffs_remount(const YCHAR *path, int force, int read_only) struct yaffs_dev *dev=NULL; yaffsfs_Handle *yh; + if(yaffsfs_CheckPath(path) < 0){ + yaffsfs_SetError(-ENAMETOOLONG); + return -1; + } + yaffsfs_Lock(); dev = yaffsfs_FindMountPoint(path); if(dev){ @@ -2031,6 +2157,11 @@ int yaffs_unmount2(const YCHAR *path, int force) int retVal=-1; struct yaffs_dev *dev=NULL; + if(yaffsfs_CheckPath(path) < 0){ + yaffsfs_SetError(-ENAMETOOLONG); + return -1; + } + yaffsfs_Lock(); dev = yaffsfs_FindMountPoint(path); if(dev){ @@ -2049,7 +2180,7 @@ int yaffs_unmount2(const YCHAR *path, int force) if(!inUse || force){ if(inUse) - yaffsfs_PutDeviceHandles(dev); + yaffsfs_BreakDeviceHandles(dev); yaffs_deinitialise(dev); retVal = 0; @@ -2081,6 +2212,11 @@ loff_t yaffs_freespace(const YCHAR *path) struct yaffs_dev *dev=NULL; YCHAR *dummy; + if(yaffsfs_CheckPath(path) < 0){ + yaffsfs_SetError(-ENAMETOOLONG); + return -1; + } + yaffsfs_Lock(); dev = yaffsfs_FindDevice(path,&dummy); if(dev && dev->is_mounted){ @@ -2100,10 +2236,16 @@ loff_t yaffs_totalspace(const YCHAR *path) struct yaffs_dev *dev=NULL; YCHAR *dummy; + if(yaffsfs_CheckPath(path) < 0){ + yaffsfs_SetError(-ENAMETOOLONG); + return -1; + } + yaffsfs_Lock(); dev = yaffsfs_FindDevice(path,&dummy); if(dev && dev->is_mounted){ - retVal = (dev->param.end_block - dev->param.start_block + 1) - dev->param.n_reserved_blocks; + retVal = (dev->param.end_block - dev->param.start_block + 1) - + dev->param.n_reserved_blocks; retVal *= dev->param.chunks_per_block; retVal *= dev->data_bytes_per_chunk; @@ -2120,6 +2262,11 @@ int yaffs_inodecount(const YCHAR *path) struct yaffs_dev *dev=NULL; YCHAR *dummy; + if(yaffsfs_CheckPath(path) < 0){ + yaffsfs_SetError(-ENAMETOOLONG); + return -1; + } + yaffsfs_Lock(); dev = yaffsfs_FindDevice(path,&dummy); if(dev && dev->is_mounted) { @@ -2250,6 +2397,11 @@ yaffs_DIR *yaffs_opendir(const YCHAR *dirname) struct yaffs_obj *obj = NULL; yaffsfs_DirectorySearchContext *dsc = NULL; + if(yaffsfs_CheckPath(dirname) < 0){ + yaffsfs_SetError(-ENAMETOOLONG); + return -1; + } + yaffsfs_Lock(); obj = yaffsfs_FindObject(NULL,dirname,0,1,NULL); @@ -2349,6 +2501,10 @@ int yaffs_symlink(const YCHAR *oldpath, const YCHAR *newpath) int retVal= -1; int mode = 0; /* ignore for now */ + if(yaffsfs_CheckPath(newpath) < 0){ + yaffsfs_SetError(-ENAMETOOLONG); + return -1; + } yaffsfs_Lock(); parent = yaffsfs_FindDirectory(NULL,newpath,&name,0); if(!parent) @@ -2361,10 +2517,10 @@ int yaffs_symlink(const YCHAR *oldpath, const YCHAR *newpath) obj = yaffs_create_symlink(parent,name,mode,0,0,oldpath); if(obj) retVal = 0; - else{ - yaffsfs_SetError(-ENOSPC); /* just assume no space for now */ - retVal = -1; - } + else if (yaffsfs_FindObject(NULL,newpath,0,0, NULL)) + yaffsfs_SetError(-EEXIST); + else + yaffsfs_SetError(-ENOSPC); } yaffsfs_Unlock(); @@ -2406,6 +2562,11 @@ int yaffs_link(const YCHAR *oldpath, const YCHAR *linkpath) struct yaffs_obj *lnk = NULL; int retVal = -1; + if(yaffsfs_CheckPath(linkpath) < 0){ + yaffsfs_SetError(-ENAMETOOLONG); + return -1; + } + yaffsfs_Lock(); obj = yaffsfs_FindObject(NULL,oldpath,0,1,NULL); @@ -2453,6 +2614,8 @@ int yaffs_mknod(const YCHAR *pathname, mode_t mode, dev_t dev) pathname=pathname; mode=mode; dev=dev; + + yaffsfs_SetError(-EINVAL); return -1; } @@ -2466,9 +2629,17 @@ int yaffs_n_handles(const YCHAR *path) { struct yaffs_obj *obj; + if(yaffsfs_CheckPath(path) < 0){ + yaffsfs_SetError(-ENAMETOOLONG); + return -1; + } + obj = yaffsfs_FindObject(NULL,path,0,1,NULL); - return yaffsfs_CountHandles(obj); + if(obj) + return yaffsfs_CountHandles(obj); + else + return -1; } int yaffs_get_error(void)