void LiveCDFS::destroy(LiveCDFS *fs) { FUNC_START("fs=", fs); t_active_livecdfs *active = findActive(fs); if (active != NULL) { active->count--; if (active->count == 0) { TRACE("fs=%p not active anymore, destroying", fs); activefs.erase((vector<t_active_livecdfs>::iterator)active); delete fs; } else { TRACE("fs=%p still has %u references", fs, active->count); } } else { ERROR("fs=%p not found, cannot destroy", fs); } FUNC_END(); }
int LiveCDFS::doRename(const char *oldname, const char *newname) { FUNC_START("old='%s', new='%s'", oldname, newname); if (!whiteout->isVisible(oldname)) { FUNC_RET("%d", -1, -1); } if (path->isDir(oldname)) { // Ok, yes I'm playing lazy - with directories, a rename // means that the old ceases to exist (whiteout), but the // new directory should contain the contents of the old // one. Pretty easy if it is only on temp, but not so // easy if it is on the root directory... (Amd we don't // really want to copy all the contents over, now do we?) ERROR("Rename of directories is currently not implemented"); FUNC_RET("%d", -1, -1); } string sold = path->mktmp(oldname); string snew = path->mktmp(newname); if (!path->exists(sold, 0)) { path->copyTmp(oldname); } int ret = rename(sold.c_str(), snew.c_str()); if (ret < 0) { ERROR("strerror(errno)='%s' on rename(old='%s', new='%s')", strerror(errno), sold.c_str(), snew.c_str()); } else { whiteout->setVisible(oldname, false); whiteout->setVisible(newname, true); } FUNC_RET("%d", ret, ret); }
static ssize_t msr3110_dev_read(struct file *filp, char __user *buf, size_t count, loff_t *offset) { ssize_t retVal = 0; unsigned char tmp[MSR3110_DEV_READ_MAX]; int loopIdx = 0; int readByteCount = 0;; FUNC_START(); my_pr_debug( "%s count: %d\n", __func__, count); if( count > MSR3110_DEV_READ_MAX) { count = MSR3110_DEV_READ_MAX; } nfc_client->addr = ( MSR3110_CMD_I2C_ID & I2C_MASK_FLAG); nfc_client->ext_flag = I2C_DMA_FLAG; nfc_client->ext_flag |= I2C_DIRECTION_FLAG; SET_NFC_CLIENT_TIMING(); SET_NFC_CLIENT_BUS_LOG(); for( loopIdx = 0; loopIdx < MSR3110_DEV_READ_RETRY_COUNT; loopIdx++) { retVal = i2c_master_recv( nfc_client, (unsigned char *)I2CDMAReadBuf_pa, count); my_pr_debug( "%s loopIdx: %d, recv retVal: %d \n", __func__, loopIdx, retVal); if( retVal == count) { my_pr_debug( "%s SUCCESS: recv. \n", __func__); break; } if( retVal < 0) { //my_pr_err( "%s FAIL: recv. CONTINUE. \n", __func__); usleep_range( 900, 1000); continue; } if( retVal > 2) { //my_pr_err( "%s FAIL: recv too many bytes. goto end. \n", __func__); //retVal = -EIO; retVal = 0; goto end; } } if( retVal < 0) { my_pr_err( "%s FAIL: recv. out of retry count, goto end. \n", __func__); retVal = 0; goto end; } readByteCount = retVal; #if 0 for( loopIdx = 0; loopIdx < MSR3110_DEV_READ_RETRY_COUNT; loopIdx++) { msleep(MSR3110_DEV_READ_RETRY_DELAY); retVal = i2c_master_recv( nfc_client, tmp, 2); my_pr_info( "%s loopIdx: %d, recv retVal: %d \n", __func__, loopIdx, retVal); if( retVal == 2) { my_pr_info( "%s SUCCESS: recv. \n", __func__); break; } if( retVal < 0) { my_pr_err( "%s FAIL: recv. CONTINUE. \n", __func__); continue; } if( retVal > 2) { my_pr_err( "%s FAIL: recv too many bytes. goto end. \n", __func__); retVal = -EIO; goto end; } } if( retVal < 0) { my_pr_err( "%s FAIL: recv. out of retry count, goto end. \n", __func__); goto end; } readByteCount = 2; if( tmp[1] > 0) { for( loopIdx = 0; loopIdx < MSR3110_DEV_READ_RETRY_COUNT; loopIdx++) { msleep(1); retVal = i2c_master_recv( nfc_client, &tmp[2], tmp[1] + 2); my_pr_info( "%s loopIdx: %d, recv retVal: %d", __func__, loopIdx, retVal); if( retVal == ( tmp[1] + 2)) { my_pr_info( "%s SUCCESS: recv data.", __func__); break; } if( retVal < 0) { my_pr_err( "%s FAIL: recv. CONTINUE.", __func__); continue; } if( retVal > ( tmp[1] + 2)) { my_pr_err( "%s FAIL: recv too many bytes. goto end.", __func__); retVal = -EIO; goto end; } } } if( retVal < 0) { my_pr_err( "%s FAIL: recv. out of retry count, goto end.", __func__); goto end; } readByteCount += tmp[1] + 2; retVal = readByteCount; #endif if ( copy_to_user( buf, I2CDMAReadBuf, readByteCount)) { my_pr_err("%s : failed to copy to user space\n", __func__); retVal = 0; goto end; } end: //for( loopIdx = 0; loopIdx < readByteCount; loopIdx++) //{ // my_pr_debug( "%s %02X", __func__, tmp[loopIdx]); //} FUNC_END(); return retVal; }
int LiveCDFS::doOpen(const char *file, unsigned mode) { unsigned flags = mode ^ O_ACCMODE; unsigned modes = mode & O_ACCMODE; FUNC_START("file='%s', mode=%u (flags=%u, modes=%u)", file, mode, flags, modes); if (!whiteout->isVisible(file)) { FUNC_RET("%d", -1, -1); } if (handles->find(file, flags, modes)) { TRACE("file='%s' already open", file); FUNC_RET("%d", 0, 0); } bool created = false; string tmppath = path->mktmp(file); string openpath = string(""); if (mode & O_CREAT) { TRACE("Flags for file='%s' is set to O_CREAT", file); string dir = path->getDir(file); if ((dir.length() != 0) && !path->isTmp(dir)) { TRACE("Creating directory dir='%s'", dir.c_str()); path->recurseMkdir(dir.c_str()); } openpath = tmppath; created = true; TRACE("Creating empty file='%s' on temp space", file); } else if ((modes == O_RDWR) || (modes == O_WRONLY)) { TRACE("Mode for file='%s' is set to O_RDWR || O_WRONLY", file); string rootpath = path->mkroot(file); if (path->exists(rootpath, S_IFREG) || path->exists(rootpath, S_IFLNK)) { TRACE("File='%s' is a regular file or symlink on root", file); if (!path->exists(tmppath, 0)) { path->copyTmp(file); } openpath = tmppath; } else if (path->exists(tmppath, S_IFREG) || path->exists(tmppath, S_IFLNK)) { TRACE("File='%s' is a regular file or symlink on tmp", file); openpath = tmppath; } else { ERROR("File='%s', is not a regular file nor symlink, cannot create copy on temp space", file); FUNC_RET("%d", -1, -1); } } else { // normal read TRACE("Mode for file='%s' is set for normal read", file); openpath = path->mkpath(file); } int fd = open(openpath.c_str(), mode, 0666); if (fd <= 0) { WARN("Unable to open file='%s', flags=%u, modes=%u", file, flags, modes); FUNC_RET("%d", -1, -1); } else if (created) { whiteout->setVisible(file, true); } // We don't really use the opened handle since lufs currently doesn't // describe the concept of a handle. This creates problems in doRead, // doWrite and doRelease where the only information passed is the // actual filename (what happens if multiples are open???) So, we take // the completely unoptimal (slow) approach in opening the file again in // doRead and doWrite (When an elegant work-around is in place, we can // use the handles infrastructure, currently it only indicates the number // of files we are busy with.) close(fd); handles->add(string(file), fd, flags, modes); TRACE("%u files currently open", handles->size()); FUNC_RET("%d", 0, 0); }
int LiveCDFS::doReaddir(const char *name, struct directory *dir) { FUNC_START("name='%s', dir=%p", name, dir); if (!whiteout->isVisible(name)) { FUNC_RET("%d", -1, -1); } DIR *rdir = NULL, *tdir = NULL; struct lufs_fattr attr; struct dirent *ent; vector<string> entries; string rootpath = path->mkroot(name); string tmppath = path->mktmp(name); if ((tdir = opendir(tmppath.c_str()))) { while ((ent = readdir(tdir))) { string subpath = path->join(name, ent->d_name); if (whiteout->isVisible(subpath)) { TRACE("Adding direntry='%s'", ent->d_name); if ((doStat(subpath.c_str(), &attr)) < 0) { ERROR("Could not stat file='%s'", ent->d_name); closedir(rdir); FUNC_RET("%d", -1, -1); } lu_cache_add2dir(dir, ent->d_name, NULL, &attr); } entries.push_back(subpath); } closedir(tdir); } else { path->recurseMkdir(name); } if (whiteout->isVisible(name) && Path::exists(rootpath, S_IFDIR) && (rdir = opendir(rootpath.c_str()))) { while ((ent = readdir(rdir))){ string subpath = path->join(name, ent->d_name); bool found = false; vector<string>::iterator i = entries.begin(); while (!found && (i != entries.end())) { if (i->compare(subpath) == 0) { found = true; } i++; } if (!found && whiteout->isVisible(subpath)) { TRACE("Adding direntry='%s'", ent->d_name); if ((doStat(subpath.c_str(), &attr)) < 0) { ERROR("could not stat file='%s'", ent->d_name); closedir(rdir); FUNC_RET("%d", -1, -1); } lu_cache_add2dir(dir, ent->d_name, NULL, &attr); } } closedir(rdir); } else { WARN("could not open directory, name='%s'", name); } FUNC_RET("%d", 0, 0); }
void LiveCDFS::doUmount() { FUNC_START(""); FUNC_END(); }
int LiveCDFS::doMount() { FUNC_START(""); FUNC_RET("%d", 1, 1); }