Ejemplo n.º 1
0
/*
 * Seek to the EODump (end-of-dump) after the given position. This is
 * the position after the EOF filemark immediately after the EODump mark.
 * This is for tapes of version 4 or greater.
 */
static afs_int32
file_SeekEODump(struct butm_tapeInfo *info, afs_int32 position)
{
    afs_int32 code = 0;
    afs_int32 blockType;
    afs_int32 w;
    struct progress *p;
    afs_int64 stopOff;	/* file seek offsets */

    if (info->debug)
	printf("butm: Seek to end-of-dump\n");
    info->error = 0;

    code = check(info, READ_OP);
    if (code)
	ERROR_EXIT(code);
    if (READS || WRITES)
	ERROR_EXIT(BUTM_BADOP);

    if (isafile) {
	p = (struct progress *)info->tmRock;
	w = USD_SEEK(p->fid, 0, SEEK_END, &stopOff);
	if (w) {
	    info->error = w;
	    ERROR_EXIT(BUTM_POSITION);
	}

	if (stopOff % BUTM_BLOCKSIZE)
	    ERROR_EXIT(BUTM_POSITION);
	info->position = (stopOff / BUTM_BLOCKSIZE);
    } else {
	/* Seek to the desired position */
	code = SeekFile(info, (position - info->position) + 1);
	if (code)
	    ERROR_EXIT(code);

	/*
	 * Search until the filemark is an EODump filemark.
	 * Skip over volumes only.
	 */
	while (1) {
	    code = ReadTapeBlock(info, tapeBlock, &blockType);
	    if (code)
		ERROR_EXIT(code);

	    if (blockType == BLOCK_EOD)
		break;
	    if (blockType != BLOCK_FMBEGIN)
		ERROR_EXIT(BUTM_BADBLOCK);

	    code = SeekFile(info, 1);	/* Step forward to next volume */
	    if (code)
		ERROR_EXIT(code);
	}
	code = 0;
    }

  error_exit:
    return (code);
}
Ejemplo n.º 2
0
void CacheFile::read(Uint8* buf,Uint32 size,Uint64 off)
{
    QMutexLocker lock(&mutex);
    bool close_again = false;

    // reopen the file if necessary
    if (fd == -1)
    {
        //	Out() << "Reopening " << path << endl;
        openFile(READ);
        close_again = true;
    }

    if (off >= file_size || off >= max_size)
    {
        throw Error(i18n("Error : Reading past the end of the file %1").arg(path));
    }

    // jump to right position
    SeekFile(fd,(Int64)off,SEEK_SET);
    if ((Uint32)::read(fd,buf,size) != size)
    {
        if (close_again)
            closeTemporary();

        throw Error(i18n("Error reading from %1").arg(path));
    }

    if (close_again)
        closeTemporary();
}
Ejemplo n.º 3
0
int main(int argc, char* argv[])
{
	char c;
	OpenFileID srcId;
	OpenFileID dstId;
	char source[255], dest[255];
	int srcSz, srcPos;
	PrintString("Input source file:");
	ReadString(source, 255);
	PrintString("Input destination file:");
	ReadString(dest, 255);
	PrintString(source);

	srcId = OpenFileFunc(source, 1);
	CreateFile(dest);
	dstId = OpenFileFunc(dest, 0);
	if (srcId == -1 || dstId == -1)
	{
		int errorId = srcId == 0 ? 1 : 2;
		PrintString("Can not open file \n");
		PrintString("Terminate program\n");
		return 0;
	}
	/* Seek source file to end of file */
	srcSz = SeekFile(-1, srcId);
	/* Seek destination file to begin of file */
	SeekFile(0, dstId);
	 
	while (srcSz>=0)
	{	
		SeekFile(srcSz, srcId);
		ReadFile(&c, 1, srcId);
		WriteFile(&c, 1, dstId);
		PrintString("Test = ");
		PrintChar(c);
		PrintChar('\n');
		srcSz --;
	}
	CloseFile(srcId);
	CloseFile(dstId);
	return 0;
}
Ejemplo n.º 4
0
/* Step to the next filemark if we are not at one already */
afs_int32
NextFile(struct butm_tapeInfo *info)
{
    afs_int32 code;

    if (!READS && !WRITES)
	return 0;

    code = SeekFile(info, 1);
    return (code);
}
Ejemplo n.º 5
0
int Archive::Scan (FILE *fp, char *szBuff, long flen)
{
      if (offset > flen)
            return 0;

      int rc;

      rc = SeekFile (fp, szBuff, offset);
      if (rc > 0)
            rc = Check (szBuff);

      return (rc > UNKNOWN ? sfxtype : rc);
}
Ejemplo n.º 6
0
void CacheFile::growFile(Uint64 to_write)
{
    // reopen the file if necessary
    if (fd == -1)
    {
        //	Out() << "Reopening " << path << endl;
        openFile(RW);
    }

    if (read_only)
        throw Error(i18n("Cannot open %1 for writing : readonly filesystem").arg(path));

    // jump to the end of the file
    SeekFile(fd,0,SEEK_END);

    if (file_size + to_write > max_size)
    {
        Out() << "Warning : writing past the end of " << path << endl;
        Out() << (file_size + to_write) << " " << max_size << endl;
    }

    Uint8 buf[1024];
    memset(buf,0,1024);
    Uint64 num = to_write;
    // write data until to_write is 0
    while (to_write > 0)
    {
        int nb = to_write > 1024 ? 1024 : to_write;
        int ret = ::write(fd,buf,nb);
        if (ret < 0)
            throw Error(i18n("Cannot expand file %1 : %2").arg(path).arg(strerror(errno)));
        else if (ret != nb)
            throw Error(i18n("Cannot expand file %1 : incomplete write").arg(path));
        to_write -= nb;
    }
    file_size += num;
//
    //	Out() << QString("growing %1 = %2").arg(path).arg(kt::BytesToString(file_size)) << endl;

    if (file_size != FileSize(fd))
    {
//			Out() << QString("Homer Simpson %1 %2").arg(file_size).arg(sb.st_size) << endl;
        fsync(fd);
        if (file_size != FileSize(fd))
        {
            throw Error(i18n("Cannot expand file %1").arg(path));
        }
    }
}
Ejemplo n.º 7
0
int main(int argc, char* argv[])
{
	OpenFileID srcId;
	OpenFileID dstId;
	char source[255], dest[255];
	int filesz,srcsz, i;
	char c;
	
	PrintString("Input source file:");
	ReadString(source, 255);
	PrintString("Input destination file:");
	ReadString(dest, 255);
	PrintString(source);

	srcId = OpenFileFunc(source, 1);
	CreateFile(dest);
	dstId = OpenFileFunc(dest, 0);
	if (srcId == -1 || dstId == -1)
	{
		int errorId = srcId == 0 ? 1 : 2;
		PrintString("Can not open file \n");
		PrintString("Terminate program\n");
		return 0;
	}
	filesz = SeekFile(-1, srcId);
	SeekFile(0, srcId);
	SeekFile(0, dstId);
	for (i = 0; i < filesz; ++i)
	{
		ReadFile(&c, 1, srcId);
		WriteFile(&c, 1, dstId);
	}
	CloseFile(srcId);
	CloseFile(dstId);
	return 0;
}
Ejemplo n.º 8
0
void CacheFile::write(const Uint8* buf,Uint32 size,Uint64 off)
{
    QMutexLocker lock(&mutex);
    bool close_again = false;

    // reopen the file if necessary
    if (fd == -1)
    {
        //	Out() << "Reopening " << path << endl;
        openFile(RW);
        close_again = true;
    }

    if (read_only)
        throw Error(i18n("Cannot open %1 for writing : readonly filesystem").arg(path));

    if (off + size > max_size)
    {
        Out() << "Warning : writing past the end of " << path << endl;
        Out() << (off + size) << " " << max_size << endl;
    }

    if (file_size < off)
    {
        //Out() << QString("Writing %1 bytes at %2").arg(size).arg(off) << endl;
        growFile(off - file_size);
    }

    // jump to right position
    SeekFile(fd,(Int64)off,SEEK_SET);
    int ret = ::write(fd,buf,size);
    if (close_again)
        closeTemporary();

    if (ret == -1)
        throw Error(i18n("Error writing to %1 : %2").arg(path).arg(strerror(errno)));
    else if ((Uint32)ret != size)
    {
        Out() << QString("Incomplete write of %1 bytes, should be %2").arg(ret).arg(size) << endl;
        throw Error(i18n("Error writing to %1").arg(path));
    }

    if (off + size > file_size)
        file_size = off + size;
}
Ejemplo n.º 9
0
static afs_int32
file_Seek(struct butm_tapeInfo *info, afs_int32 position)
{
    afs_int32 code = 0;
    afs_int32 w;
    osi_lloff_t posit;
    struct progress *p;
    afs_int64 stopOff;	/* for normal file(non-tape)  seeks  */

    if (info->debug)
	printf("butm: Seek to the tape position %d\n", position);

    info->error = 0;

    code = check(info, READ_OP);
    if (code)
	ERROR_EXIT(code);

    if (isafile) {
	p = (struct progress *)info->tmRock;
	posit = (osi_lloff_t) position *(osi_lloff_t) BUTM_BLOCKSIZE;

	w = USD_SEEK(p->fid, posit, SEEK_SET, &stopOff);
	if (w)
	    info->error = w;
	if (posit != stopOff)
	    ERROR_EXIT(BUTM_POSITION);

	p->reading = p->writing = 0;
	info->position = position;
    } else {
	/* Don't position backwards if we are in-between FMs */
	if ((READS || WRITES) && ((position - info->position) <= 0))
	    ERROR_EXIT(BUTM_BADOP);

	code = SeekFile(info, (position - info->position));
	if (code)
	    ERROR_EXIT(code);
    }

  error_exit:
    return (code);
}
Ejemplo n.º 10
0
// ---------------------------------------------------------------------------
// Name:        RawDataReader::RawDataInitialize
// Description: This function will open the raw file and read the configuration records.
// Author:      Rajeeb Barman
// Date:        26/09/2013
// ---------------------------------------------------------------------------
AMDTResult RawDataReader::RawDataInitialize(const wchar_t* pFileName, bool isOnline)
{
    pFileName = pFileName;

    AMDTInt32 ret = 0;
    g_isOnline = isOnline;

    if (!g_isOnline)
    {
#if 0 //File support
        //Open the raw data file
        ret = OpenFile(&m_hRawFile, pFileName, L"rb");

        if (m_hRawFile == NULL)
        {
            ret = AMDT_ERROR_FAIL;
        }

        if (AMDT_STATUS_OK == ret)
        {
            //read file to a buffer
            SeekFile(m_hRawFile, 0, SEEK_SET);
            size = ReadFile(m_hRawFile, (AMDTUInt8*) m_fileBuffer, FILE_BUFFER_SIZE);
        }

#endif
    }
    else
    {
        //If online, read from buffer
        AMDTUInt32 clientIdx = 0;
        FILE_HEADER header;
        AMDTUInt32 res = 0;

        ret = GetPowerDriverClientId(&clientIdx);

        if (AMDT_STATUS_OK == ret)
        {
            header.ulClientId = clientIdx;
            header.ulBufferId = 0;
            header.uliBuffer = reinterpret_cast<uint64>(m_pBufferHeader);
            ret = CommandPowerDriver(DRV_CMD_TYPE_IN_OUT,
                                     IOCTL_GET_FILE_HEADER_BUFFER,
                                     &header,
                                     sizeof(FILE_HEADER),
                                     &header,
                                     sizeof(FILE_HEADER),
                                     &res);
        }
    }

    if (AMDT_STATUS_OK == ret)
    {
        //First section of the raw data file is file header
        ret = ReadFileHeader();
    }

    if (AMDT_STATUS_OK == ret)
    {
        //Allocate memory for a raw buffer chunk.
        m_offset = m_rawDataHdl.m_fileHdr.m_rawDataOffset;

        //Read section headers
        ret = ReadSections();
    }

    if (AMDT_STATUS_OK == ret)
    {
        if (!g_isOnline)
        {
            //Calculate the length of the file
            PwrSeekFile(m_hRawFile, 0, SEEK_END);
            m_fileLen = ftell(m_hRawFile);

            //Raw record offset;
            m_curr = m_offset = m_rawDataHdl.m_fileHdr.m_rawDataOffset;
            m_onlineOffset = m_offset;
        }
    }

    return ret;
}
Ejemplo n.º 11
0
//===============================================================================
// This loads the program "name" into memory, if it exists.
//===============================================================================
long DoExec(char *name, char *environment)
{
	struct FCB *fHandle;
	long argv, argc;
	int retval = -ENOEXEC;
	struct Message *FSMsg = ALLOCMSG;

	char *kname = AllocKMem((size_t) strlen(name) + 6); // Enough space for "/bin" + name

	strcpy(kname, "/bin/");
	strcat(kname, name);

	// Open file
	FSMsg->nextMessage = 0;
	FSMsg->byte = OPENFILE;
	FSMsg->quad1 = (long) kname;
	FSMsg->quad2 = (long) fHandle;
	SendReceiveMessage(FSPort, FSMsg);

	fHandle = (struct FCB *) FSMsg->quad1;

	if ((long) fHandle > 0)
	{
		char magic[5];
		char executable = 0;
		(void) SeekFile(FSMsg, fHandle, 10, SEEK_SET);
		(void) ReadFromFile(fHandle, magic, 4);
		magic[4] = 0;
		if (!strcmp(magic, "IJ64"))
		{
			(void) SeekFile(FSMsg, fHandle, 0, SEEK_SET);
			LoadFlat(fHandle);
			executable = 1;
		}
		else
		{
			(void) SeekFile(FSMsg, fHandle, 0, SEEK_SET);
			(void) ReadFromFile(fHandle, magic, 4);
			if (magic[0] == 0x7F)
			{
				(void) SeekFile(FSMsg, fHandle, 0, SEEK_SET);
				LoadElf(FSMsg, fHandle);
				executable = 1;
			}
		}

		//Close file and deallocate memory for structures
		FSMsg->nextMessage = 0;
		FSMsg->byte = CLOSEFILE;
		FSMsg->quad1 = (long) fHandle;
		SendReceiveMessage(FSPort, FSMsg);
		DeallocMem(kname);
		DeallocMem(FSMsg);

		if (executable)
		{
			long *l;

			// Process the arguments for argc and argv
			// Copy environment string to user data space
			// It occupies the 81 bytes after the current first free memory
			currentTask->environment = (void *) currentTask->firstfreemem;
			memcpy(currentTask->environment, environment, 80);
			currentTask->firstfreemem += 80;
			argv = (long) currentTask->environment;
			argc = ParseEnvironmentString(&argv);
			argv += 80;

			// Adjust firstfreemem to point to the first free memory location.
			currentTask->firstfreemem += argc * sizeof(char *);

			// Build the first MemStruct struct. Is all this necessary? User tasks don't use the kernel memory allocation, do they?
			l = (long *) (currentTask->firstfreemem);
			*l = 0;
			*(l + 1) = -(long) (((sizeof(struct MemStruct)
					+ currentTask->firstfreemem)) % PageSize);
			asm("mov %0,%%rdi;" "mov %1,%%rsi":
					: "r"(argc), "r"(argv):"%rax", "%rdi");
			return 0;
		}
		else
			return retval;
Ejemplo n.º 12
0
void    IOPrologue( void ) {
//====================

    ftnfile     *fcb;
    byte        form;
    byte        accm;

    IOCB->typ = PT_NOT_STARTED;
    if( IOCB->flags & BAD_REC ) {
        IOErr( IO_IREC );
    }
    if( IOCB->set_flags & SET_INTERNAL ) {
        F_Connect();
    } else {
        ChkUnitId();
        FindFtnFile();
        if( IOCB->fileinfo == NULL ) {
            IOCB->set_flags &= ~SET_FILENAME;
            ConnectFile();
        }
    }
    fcb = IOCB->fileinfo;
    if( fcb->action == ACT_DEFAULT ) {
        fcb->action = ACTION_RW;
    }
    ChkIOOperation( fcb );
    if( fcb->cctrl == CC_DEFAULT ) {
        fcb->cctrl = CC_NO;
    }
    accm = fcb->accmode;
    if( accm == ACCM_DEFAULT ) {
        if( IOCB->set_flags & SET_RECORDNUM ) {
            accm = ACCM_DIRECT;
        } else {
            accm = ACCM_SEQUENTIAL;
        }
        fcb->accmode = accm;
    } else {
        if( ( accm == ACCM_DIRECT ) && (IOCB->set_flags & SET_RECORDNUM) == 0 ) {
            IOErr( IO_REC1_ACCM );
        } else if( ( ( accm == ACCM_SEQUENTIAL ) || ( accm == ACCM_APPEND ) ) &&
                   (IOCB->set_flags & SET_RECORDNUM) ) {
            IOErr( IO_REC2_ACCM );
        }
    }
    if( accm == ACCM_DIRECT ) {
        fcb->recnum = IOCB->recordnum; // set up recordnumber
    }
    form = fcb->formatted;
    if( form == 0 ) {                    // set up format if it was
        if( (IOCB->flags & IOF_NOFMT) == 0 ) {     // not previously set
            form = FORMATTED_IO;
        } else {
            form = UNFORMATTED_IO;
        }
        fcb->formatted = form;
    } else {
        if( (form == FORMATTED_IO) && (IOCB->flags & IOF_NOFMT) ) {
            IOErr( IO_AF1 );
        } else if( (form == UNFORMATTED_IO) && (IOCB->flags & IOF_NOFMT) == 0 ) {
            IOErr( IO_AF2 );
        }
    }
    if( fcb->internal != NULL ) {
        fcb->bufflen = fcb->internal->len;
        fcb->buffer = RChkAlloc( fcb->bufflen );
    } else {
        if( ( accm <= ACCM_SEQUENTIAL ) &&
            ( fcb->eofrecnum != 0 ) &&
            ( fcb->recnum >= fcb->eofrecnum ) &&
            // Consider: READ( 1, *, END=10 )
            //           ...
            //     10    WRITE( 1, * ) 'write after EOF'
            // if an EOF condition was encounterd, we don't want IO_PAST_EOF
            // on the write
            (IOCB->flags & IOF_OUTPT) == 0 ) {
            if( fcb->recnum != fcb->eofrecnum ) {
                IOErr( IO_PAST_EOF );
            } else {
                fcb->recnum++;
                SysEOF();
            }
        }
        _AllocBuffer( fcb );
        if( fcb->fileptr == NULL ) {
            DoOpen();
        }
        if( fcb->accmode == ACCM_DIRECT ) {
            SeekFile( fcb );
            ChkIOErr( fcb );
        }
        fcb->col = 0;
    }
    if( (IOCB->flags & IOF_OUTPT) && ( fcb->col == 0 ) ) {
        memset( fcb->buffer, ' ', fcb->bufflen );
    }
}
Ejemplo n.º 13
0
/*
 * Execute command.
 */
void
DoCommand(
	Client_t *cli)
{
	int rc;
	char *cmd_name;
	char *lasts;
	char *msg;

	rc = 0;
	SetErrno = 0;

	msg = cli->cmdbuf;
	/*
	 * Extract command name.
	 */
/* LINTED improper pointer/integer combination */
	cmd_name = strtok_r(msg, " ", &lasts);

	if (strcmp(cmd_name, SAMRFT_CMD_CONNECT) == 0) {
		SendReply(cli, "%s %d %d", SAMRFT_CMD_CONNECT, 0, 0);

	} else if (strcmp(cmd_name, SAMRFT_CMD_CONFIG) == 0) {
		char *hostname;
		int blksize;
		int tcpwindowsize;

		hostname = getString(&lasts);
		blksize = GetCfgBlksize();
		tcpwindowsize = GetCfgTcpWindowsize();

		SamStrdup(cli->hostname, hostname);
		rc = CreateCrew(cli, 1, blksize);

		SendReply(cli, "%s %d %d %d %d",
		    SAMRFT_CMD_CONFIG, rc, 1, blksize, tcpwindowsize);

	} else if (strcmp(cmd_name, SAMRFT_CMD_OPEN) == 0) {
		char *filename;
		int oflag;
		SamrftCreateAttr_t creat;

		filename = getString(&lasts);
		oflag = getInteger(&lasts);

		if (getInteger(&lasts)) {
			(void) memset((char *)&creat, 0,
			    sizeof (SamrftCreateAttr_t));
			creat.mode = getInteger(&lasts);
			creat.uid = getInteger(&lasts);
			creat.gid = getInteger(&lasts);
			rc = OpenFile(cli, filename, oflag, &creat);
		} else {
			rc = OpenFile(cli, filename, oflag, NULL);
		}

		SendReply(cli, "%s %d %d", SAMRFT_CMD_OPEN, rc, errno);

	} else if (strcmp(cmd_name, SAMRFT_CMD_DPORT) == 0) {
		struct sockaddr_in data;
		int seqnum;
		char *addr = (char *)&data.sin_addr;
		char *port = (char *)&data.sin_port;

		(void) memset((char *)&data, 0, sizeof (struct sockaddr_in));
		data.sin_family = AF_INET;

		seqnum = getInteger(&lasts);

		/*
		 * Addr.
		 */
		addr[0] = getInteger(&lasts);
		addr[1] = getInteger(&lasts);
		addr[2] = getInteger(&lasts);
		addr[3] = getInteger(&lasts);

		/*
		 * Port.
		 */
		port[0] = getInteger(&lasts);
		port[1] = getInteger(&lasts);

		rc = InitDataConnection(cli, "r", seqnum,
		    data.sin_family, (struct sockaddr *)&data);
		SendReply(cli, "%s %d %d", SAMRFT_CMD_DPORT, rc, errno);

	} else if (strcmp(cmd_name, SAMRFT_CMD_DPORT6) == 0) {
		struct sockaddr_in6 data;
		struct sockaddr_in *data4 = (struct sockaddr_in *)&data;
		int i;
		int seqnum;
		char *addr;
		char *port;

		(void) memset((char *)&data, 0, sizeof (struct sockaddr_in6));

		seqnum = getInteger(&lasts);

		/*
		 * Address family.
		 */
		data.sin6_family = getInteger(&lasts);
		if (data.sin6_family == AF_INET6) {
			addr = (char *)&data.sin6_addr;
			port = (char *)&data.sin6_port;
		} else {
			addr = (char *)&data4->sin_addr;
			port = (char *)&data4->sin_port;
		}

		/*
		 * Addr.
		 */
		for (i = 0; i < 16; i++) {
			addr[i] = getInteger(&lasts);
		}

		/*
		 * Port.
		 */
		port[0] = getInteger(&lasts);
		port[1] = getInteger(&lasts);

		rc = InitDataConnection(cli, "r", seqnum,
		    data.sin6_family, (struct sockaddr *)&data);
		SendReply(cli, "%s %d %d", SAMRFT_CMD_DPORT6, rc, errno);

	} else if (strcmp(cmd_name, SAMRFT_CMD_STOR) == 0) {
		fsize_t nbytes;

		nbytes = getLongLong(&lasts);
		rc = ReceiveData(cli, nbytes);

	} else if (strcmp(cmd_name, SAMRFT_CMD_SEND) == 0) {
		size_t nbytes;

		nbytes = getInteger(&lasts);

		rc = ReceiveData(cli, nbytes);
		SendReply(cli, "%s %d %d", SAMRFT_CMD_SEND, rc, errno);

	} else if (strcmp(cmd_name, SAMRFT_CMD_RECV) == 0) {
		size_t nbytes;

		nbytes = getInteger(&lasts);

		/*
		 * Process receive command from client.  Send data from local
		 * file over data sockets to the client process.
		 */
		rc = SendData(cli, nbytes);
		SendReply(cli, "%s %d %d", SAMRFT_CMD_RECV, rc, errno);

	} else if (strcmp(cmd_name, SAMRFT_CMD_SEEK) == 0) {
		off64_t setpos;
		int whence;
		off64_t offset;

		setpos = getLongLong(&lasts);
		whence = getInteger(&lasts);

		rc = SeekFile(cli, setpos, whence, &offset);
		SendReply(cli, "%s %d %d %lld", SAMRFT_CMD_SEEK,
		    rc, errno, offset);

	} else if (strcmp(cmd_name, SAMRFT_CMD_FLOCK) == 0) {
		int type;

		type = getInteger(&lasts);

		rc = FlockFile(cli, type);
		SendReply(cli, "%s %d %d", SAMRFT_CMD_FLOCK, rc, errno);

	} else if (strcmp(cmd_name, SAMRFT_CMD_ARCHIVEOP) == 0) {
		char *path;
		char *ops;

		path = getString(&lasts);
		ops = getString(&lasts);

		rc = sam_archive(path, ops);
		SendReply(cli, "%s %d %d", SAMRFT_CMD_ARCHIVEOP, rc, errno);

	} else if (strcmp(cmd_name, SAMRFT_CMD_CLOSE) == 0) {

		rc = CloseFile(cli);
		SendReply(cli, "%s %d %d", SAMRFT_CMD_CLOSE, rc, errno);

	} else if (strcmp(cmd_name, SAMRFT_CMD_UNLINK) == 0) {
		char *name;

		name = getString(&lasts);

		rc = UnlinkFile(cli, name);
		SendReply(cli, "%s %d %d", SAMRFT_CMD_UNLINK, rc, errno);

	} else if (strcmp(cmd_name, SAMRFT_CMD_DISCONN) == 0) {

		Trace(TR_DEBUG, "RFT disconnect, no reply: '%s'", cli->cmdbuf);
		CleanupCrew(cli);
		cli->disconnect = 1;

		/*
		 * No reply.
		 */

	} else if (strcmp(cmd_name, SAMRFT_CMD_ISMOUNTED) == 0) {
		int mounted;
		char *mount_point;

		mount_point = getString(&lasts);

		mounted = IsMounted(cli, mount_point);
		SendReply(cli, "%s %d", SAMRFT_CMD_ISMOUNTED, mounted);

	} else if (strcmp(cmd_name, SAMRFT_CMD_STAT) == 0) {
		struct stat64 buf;
		char *filename;

		filename = getString(&lasts);

		(void) memset(&buf, 0, sizeof (buf));
		rc = stat64(filename, &buf);
		SendReply(cli, "%s %d %d %d %d %d %lld",
		    SAMRFT_CMD_STAT, rc, errno,
		    buf.st_mode, buf.st_uid, buf.st_gid, buf.st_size);

	} else if (strcmp(cmd_name, SAMRFT_CMD_STATVFS) == 0) {
		struct statvfs64 buf;
		char *mount_point;
		int offlineFiles;
		fsize_t offlineFileSize;

		mount_point = getString(&lasts);
		offlineFiles = getInteger(&lasts);

		(void) memset(&buf, 0, sizeof (buf));
		rc = statvfs64(mount_point, &buf);

		if (rc == 0 && (strcmp(buf.f_basetype, "samfs") == 0) &&
		    offlineFiles == B_TRUE) {
			offlineFileSize = DiskVolsOfflineFiles(mount_point);
			/*
			 * Adjust capacity to include size of offline files.
			 */
			buf.f_blocks += offlineFileSize / buf.f_frsize;
		}

		SendReply(cli, "%s %d %d %lld %lld %ld %s",
		    SAMRFT_CMD_STATVFS, rc, errno,
		    buf.f_bfree, buf.f_blocks, buf.f_frsize, buf.f_basetype);

	} else if (strcmp(cmd_name, SAMRFT_CMD_SPACEUSED) == 0) {
		char *path;
		fsize_t spaceUsed;

		path = getString(&lasts);

		spaceUsed = DiskVolsAccumSpaceUsed(path);

		SendReply(cli, "%s %d %d %lld",
		    SAMRFT_CMD_SPACEUSED, rc, errno, spaceUsed);

	} else if (strcmp(cmd_name, SAMRFT_CMD_MKDIR) == 0) {
		char *dirname;
		int mode, uid, gid;

		dirname = getString(&lasts);
		mode = getInteger(&lasts);
		uid = getInteger(&lasts);
		gid = getInteger(&lasts);

		rc = MkDir(cli, dirname, mode, uid, gid);
		SendReply(cli, "%s %d %d", SAMRFT_CMD_MKDIR, rc, errno);

	} else if (strcmp(cmd_name, SAMRFT_CMD_OPENDIR) == 0) {
		char *dirname;
		int dirp;

		dirname = getString(&lasts);

		rc = OpenDir(cli, dirname, &dirp);
		SendReply(cli, "%s %d %d %d", SAMRFT_CMD_OPENDIR,
		    rc, errno, dirp);

	} else if (strcmp(cmd_name, SAMRFT_CMD_READDIR) == 0) {
		int dirp;
		SamrftReaddirInfo_t dir_info;

		dirp = getInteger(&lasts);

		rc = ReadDir(cli, dirp, &dir_info);
		if (rc == 0) {
			SendReply(cli, "%s %d %d %s %d", SAMRFT_CMD_READDIR,
			    rc, errno, dir_info.name, dir_info.isdir);
		} else {
			SendReply(cli, "%s %d %d", SAMRFT_CMD_READDIR,
			    rc, errno);
		}

	} else if (strcmp(cmd_name, SAMRFT_CMD_CLOSEDIR) == 0) {
		int dirp;

		dirp = getInteger(&lasts);

		CloseDir(cli, dirp);
		SendReply(cli, "%s %d %d", SAMRFT_CMD_CLOSEDIR, 0, 0);

	} else if (strcmp(cmd_name, SAMRFT_CMD_RMDIR) == 0) {
		char *dirname;

		dirname = getString(&lasts);

		rc = RmDir(cli, dirname);
		SendReply(cli, "%s %d %d", SAMRFT_CMD_CLOSEDIR, rc, errno);

	} else if (strcmp(cmd_name, SAMRFT_CMD_LOADVOL) == 0) {
		struct sam_rminfo rb;
		int oflag;

		/*
		 * Create sam_rminfo structure used to create
		 * a removable-media file.
		 */
		(void) memset(&rb, 0, sizeof (rb));

		rb.flags = getInteger(&lasts);

		(void) strncpy(rb.file_id,  getString(&lasts),
		    sizeof (rb.file_id));
		(void) strncpy(rb.owner_id, getString(&lasts),
		    sizeof (rb.owner_id));
		(void) strncpy(rb.group_id, getString(&lasts),
		    sizeof (rb.group_id));

		rb.n_vsns = 1;
		(void) strncpy(rb.media, getString(&lasts), sizeof (rb.media));
		(void) strncpy(rb.section[0].vsn, getString(&lasts),
		    sizeof (rb.section[0].vsn));

		oflag = getInteger(&lasts);

		rc = LoadVol(cli, &rb, oflag);

		SendReply(cli, "%s %d %d", SAMRFT_CMD_LOADVOL, rc, errno);

	} else if (strcmp(cmd_name, SAMRFT_CMD_GETVOLINFO) == 0) {
		struct sam_rminfo getrm;
		int eq;

		rc = GetVolInfo(cli, &getrm, &eq);

		SendReply(cli, "%s %d %d %d %lld %d", SAMRFT_CMD_GETVOLINFO,
		    rc, errno, getrm.block_size, getrm.position, eq);

	} else if (strcmp(cmd_name, SAMRFT_CMD_SEEKVOL) == 0) {
		int block;

		block = getInteger(&lasts);

		rc = SeekVol(cli, block);

		SendReply(cli, "%s %d %d", SAMRFT_CMD_SEEKVOL, rc, errno);

	} else if (strcmp(cmd_name, SAMRFT_CMD_UNLOADVOL) == 0) {
		struct sam_ioctl_rmunload unload;

		/*
		 * Create sam_rmunload structure used to unload
		 * a removable-media file.
		 */
		(void) memset(&unload, 0, sizeof (unload));

		unload.flags = getInteger(&lasts);

		rc = UnloadVol(cli, &unload);

		SendReply(cli, "%s %d %d %lld", SAMRFT_CMD_UNLOADVOL,
		    rc, errno, unload.position);
	} else {
		Trace(TR_ERR, "Unknown RFT command: %s", cmd_name);
	}
}
Ejemplo n.º 14
0
int ZipFile::ExtractFile(int ind, const char *dest, bool withpath)
{
    if(!SwitchMode(OPEN))
        return -1;

    if(!SeekFile(ind) && ind < RealArchiveItemCount)
        return -1;

    ArchiveFileStruct * CurArcFile = GetFileStruct(ind);

    u32 done = 0;

	char * RealFilename = strrchr(CurArcFile->filename, '/');
	if(RealFilename)
        RealFilename += 1;
    else
        RealFilename = CurArcFile->filename;

	char writepath[1024];
	if(withpath)
        snprintf(writepath, sizeof(writepath), "%s/%s", dest, CurArcFile->filename);
    else
        snprintf(writepath, sizeof(writepath), "%s/%s", dest, RealFilename);

	u32 filesize = CurArcFile->length;

    if(CurArcFile->isdir)
    {
        strncat(writepath, "/", sizeof(writepath));
        CreateSubfolder(writepath);
        return 1;
    }

    int ret = unzOpenCurrentFile(uzFile);

    if(ret != UNZ_OK)
        return -2;

    char * temppath = strdup(writepath);
    char * pointer = strrchr(temppath, '/');
    if(pointer)
    {
        pointer += 1;
        pointer[0] = '\0';
    }

    CreateSubfolder(temppath);

    free(temppath);
    temppath = NULL;

    u32 blocksize = 1024*50;
    void *buffer = malloc(blocksize);

    FILE *pfile = fopen(writepath, "wb");
    if(!pfile)
    {
        unzCloseCurrentFile(uzFile);
        free(buffer);
        fclose(pfile);
        WindowPrompt(("Could not extract file:"), CurArcFile->filename, "OK", NULL);
        return -3;
    }

    do
    {
        if(filesize - done < blocksize)
            blocksize = filesize - done;

        ret = unzReadCurrentFile(uzFile, buffer, blocksize);
        if(ret < 0)
        {
            free(buffer);
            fclose(pfile);
            unzCloseCurrentFile(uzFile);
            return -4;
        }

        fwrite(buffer, 1, blocksize, pfile);

        done += ret;

    } while(done < filesize);

    fclose(pfile);
    unzCloseCurrentFile(uzFile);

    free(buffer);

    return 1;
}
Ejemplo n.º 15
0
static afs_int32
ReadTapeBlock(struct butm_tapeInfo *info,
	      char *buffer, /* assumed to be 16384 bytes */
	      afs_int32 *blockType)
{
    afs_int32 code = 0;
    afs_int32 rsize, fmtype;
    struct tapeLabel *label;
    struct fileMark *fmark;
    struct blockMark *bmark;
    struct progress *p;

    *blockType = BLOCK_UNKNOWN;

    p = (struct progress *)info->tmRock;

    memset(buffer, 0, BUTM_BLOCKSIZE);
    label = (struct tapeLabel *)buffer;
    fmark = (struct fileMark *)buffer;
    bmark = (struct blockMark *)buffer;

    rsize = readData(p->fid, buffer, BUTM_BLOCKSIZE, &info->error);
    if (rsize > 0) {
	incPosition(info, p->fid, rsize);
	p->reading++;
    }

    if (rsize == 0) {		/* Read a HW EOF Marker? OK */
	*blockType = BLOCK_EOF;
	incSize(info, config.fileMarkSize);	/* Size of filemark */
	if (!isafile)
	    info->position++;	/* bump position */
	p->reading = 0;		/* No reads since EOF */
    }

    else if (rsize != BUTM_BLOCKSIZE) {	/* Didn't Read a full block */
	info->status |= BUTM_STATUS_READERROR;
	ERROR_EXIT((rsize < 0) ? BUTM_IO : BUTM_EOT);
    }

    else if (ntohl(bmark->magic) == BLOCK_MAGIC) {	/* Data block? */
	*blockType = BLOCK_DATA;
    }

    else if (ntohl(fmark->magic) == FILE_MAGIC) {	/* Read a filemark? */
	fmtype = ntohl(fmark->nBytes);

	if (fmtype == FILE_BEGIN) {	/* filemark begin */
	    *blockType = BLOCK_FMBEGIN;
	} else if (fmtype == FILE_FMEND) {	/* filemark end */
	    *blockType = BLOCK_FMEND;
	    code = SeekFile(info, 1);
	} else if (fmtype == FILE_EOD) {	/* EOD mark */
	    *blockType = BLOCK_EOD;
	    info->status |= BUTM_STATUS_EOD;
	    code = SeekFile(info, 1);
	}
    }

    else if (ntohl(label->magic) == TAPE_MAGIC) {	/* Read a tape label? */
	*blockType = BLOCK_LABEL;
	code = SeekFile(info, 1);
    }

    if (isafile)
	info->position++;

  error_exit:
    return (code);
}
Ejemplo n.º 16
0
void SaveNodeList(NodesX *nodesx,const char *filename)
{
 index_t i;
 int fd;
 NodesFile nodesfile={0};
 index_t super_number=0;
 ll_bin2_t latlonbin=0,maxlatlonbins;
 index_t *offsets;

 /* Print the start message */

 printf_first("Writing Nodes: Nodes=0");

 /* Allocate the memory for the geographical offsets array */

 offsets=(index_t*)malloc((nodesx->latbins*nodesx->lonbins+1)*sizeof(index_t));

 assert(offsets); /* Check malloc() worked */

 latlonbin=0;

 /* Re-open the file */

 nodesx->fd=ReOpenFile(nodesx->filename);

 /* Write out the nodes data */

 fd=OpenFileNew(filename);

 SeekFile(fd,sizeof(NodesFile)+(nodesx->latbins*nodesx->lonbins+1)*sizeof(index_t));

 for(i=0;i<nodesx->number;i++)
   {
    NodeX nodex;
    Node node;
    ll_bin_t latbin,lonbin;
    ll_bin2_t llbin;

    ReadFile(nodesx->fd,&nodex,sizeof(NodeX));

    /* Create the Node */

    node.latoffset=latlong_to_off(nodex.latitude);
    node.lonoffset=latlong_to_off(nodex.longitude);
    node.firstseg=nodex.id;
    node.allow=nodex.allow;
    node.flags=nodex.flags;

    if(node.flags&NODE_SUPER)
       super_number++;

    /* Work out the offsets */

    latbin=latlong_to_bin(nodex.latitude )-nodesx->latzero;
    lonbin=latlong_to_bin(nodex.longitude)-nodesx->lonzero;
    llbin=lonbin*nodesx->latbins+latbin;

    for(;latlonbin<=llbin;latlonbin++)
       offsets[latlonbin]=i;

    /* Write the data */

    WriteFile(fd,&node,sizeof(Node));

    if(!((i+1)%10000))
       printf_middle("Writing Nodes: Nodes=%"Pindex_t,i+1);
   }

 /* Close the file */

 nodesx->fd=CloseFile(nodesx->fd);

 /* Finish off the offset indexing and write them out */

 maxlatlonbins=nodesx->latbins*nodesx->lonbins;

 for(;latlonbin<=maxlatlonbins;latlonbin++)
    offsets[latlonbin]=nodesx->number;

 SeekFile(fd,sizeof(NodesFile));
 WriteFile(fd,offsets,(nodesx->latbins*nodesx->lonbins+1)*sizeof(index_t));

 free(offsets);

 /* Write out the header structure */

 nodesfile.number=nodesx->number;
 nodesfile.snumber=super_number;

 nodesfile.latbins=nodesx->latbins;
 nodesfile.lonbins=nodesx->lonbins;

 nodesfile.latzero=nodesx->latzero;
 nodesfile.lonzero=nodesx->lonzero;

 SeekFile(fd,0);
 WriteFile(fd,&nodesfile,sizeof(NodesFile));

 CloseFile(fd);

 /* Print the final message */

 printf_last("Wrote Nodes: Nodes=%"Pindex_t,nodesx->number);
}
Ejemplo n.º 17
0
void App_ASRTask(void *pdata)
{
	unsigned char tempResult;
	unsigned char err;
	unsigned short temp;
#if OS_CRITICAL_METHOD == 3/* Allocate storage for CPU status register      */
	OS_CPU_SR  cpu_sr = 0;
#endif
	(void)pdata;
	while (1)
	{
		if(myRobot.ld3320State.mode==LD_MODE_ASR_RUN)
		{			
			switch(myRobot.ld3320State.state)
			{
				case LD_ASR_RUNING:
					break;
				case LD_ASR_ERROR:		
					break;
				case LD_ASR_NONE:
				{
					myRobot.ld3320State.state=LD_ASR_RUNING;
					if (RunASR()==0)															
					{
						myRobot.ld3320State.state = LD_ASR_ERROR;
					
					}
					break;						 
				}
				case LD_ASR_FOUNDOK:
				{
		
					tempResult = LD_GetResult();											
					switch(tempResult)
					{
						case 0: 	
							break;
						case 1:
							say(myName);
							break;
						case 2:
							say(myPlace);
							break;
						case 3:
							say(yourName);
							break;
						case 4: 
							motorSpeed(20,1,1);
							break;
						case 5: 
							Stop(1);
							break;
						case 6:
							err = f_open(&lis, MUSICLIS_DIR, FA_OPEN_EXISTING | FA_READ );
							if (err == FR_OK)
							{
								//打开成功,开始查找文件
								err = SeekFile(&lis, 47, myRobot.ld3320State.filename, &temp);//查找列表文件,得到文件名,并将其保存至filename中
								if (err == 0)//没有错误就改变音乐播放状态,并发送信号量,表示可以播放.
								{
									myRobot.ld3320State.mp3State = MP3_NEW_PLAY;

									OSSemPost(Mp3TransSem); //再次添加信号量
								}//
								
								//关闭文件
								f_close(&lis);
							
							}
							break;
						case 7: 
							err = f_open(&lis, ACTION_DIR, FA_OPEN_EXISTING | FA_READ );
							if (err == FR_OK)
							{
								err = SeekFile(&lis, 3, myRobot.actionctrl.filename, &temp);
								if (err == 0)
								{
									myRobot.actionctrl.status |= ACTION_START;
									if (temp & ACTION_BASIC)	//如果是基本动作,则将基本动作标志置位
										myRobot.actionctrl.status |= ACTION_BASIC;
									else
										myRobot.actionctrl.status &= ~ACTION_BASIC;
									f_close(&lis);
									OSSemPost(ActionSem);
									//在此添加信号量
								}
							}
							break;
						case 8:	
							err = f_open(&lis, ACTION_DIR, FA_OPEN_EXISTING | FA_READ );
							if (err == FR_OK)
							{
								err = SeekFile(&lis, 4, myRobot.actionctrl.filename, &temp);
								if (err == 0)
								{
									myRobot.actionctrl.status |= ACTION_START;
									if (temp & ACTION_BASIC)	//如果是基本动作,则将基本动作标志置位
										myRobot.actionctrl.status |= ACTION_BASIC;
									else
										myRobot.actionctrl.status &= ~ACTION_BASIC;
									f_close(&lis);
									OSSemPost(ActionSem);
									//在此添加信号量
								}
							}
							break;
						case 9:
							err = f_open(&lis, ACTION_DIR, FA_OPEN_EXISTING | FA_READ );
							if (err == FR_OK)
							{
								err = SeekFile(&lis, 7, myRobot.actionctrl.filename, &temp);
								if (err == 0)
								{
									myRobot.actionctrl.status |= ACTION_START;
									if (temp & ACTION_BASIC)	//如果是基本动作,则将基本动作标志置位
										myRobot.actionctrl.status |= ACTION_BASIC;
									else
										myRobot.actionctrl.status &= ~ACTION_BASIC;
									f_close(&lis);
									OSSemPost(ActionSem);
									//在此添加信号量
								}
							}
							break;
						case 10:
							err = f_open(&lis, ACTION_DIR, FA_OPEN_EXISTING | FA_READ );
							if (err == FR_OK)
							{
								err = SeekFile(&lis, 8, myRobot.actionctrl.filename, &temp);
								if (err == 0)
								{
									myRobot.actionctrl.status |= ACTION_START;
									if (temp & ACTION_BASIC)	//如果是基本动作,则将基本动作标志置位
										myRobot.actionctrl.status |= ACTION_BASIC;
									else
										myRobot.actionctrl.status &= ~ACTION_BASIC;
									f_close(&lis);
									OSSemPost(ActionSem);
									//在此添加信号量
								}
							}
							break;
						case 11:
							err = f_open(&lis, ACTION_DIR, FA_OPEN_EXISTING | FA_READ );
							if (err == FR_OK)
							{
								err = SeekFile(&lis, 32, myRobot.actionctrl.filename, &temp);
								if (err == 0)
								{
									myRobot.actionctrl.status |= ACTION_START;
									if (temp & ACTION_BASIC)	//如果是基本动作,则将基本动作标志置位
										myRobot.actionctrl.status |= ACTION_BASIC;
									else
										myRobot.actionctrl.status &= ~ACTION_BASIC;
									f_close(&lis);
									OSSemPost(ActionSem);
									//在此添加信号量
								}
							}
							break;
						case 12:
							err = f_open(&lis, ACTION_DIR, FA_OPEN_EXISTING | FA_READ );
							if (err == FR_OK)
							{
								err = SeekFile(&lis, 33, myRobot.actionctrl.filename, &temp);
								if (err == 0)
								{
									myRobot.actionctrl.status |= ACTION_START;
									if (temp & ACTION_BASIC)	//如果是基本动作,则将基本动作标志置位
										myRobot.actionctrl.status |= ACTION_BASIC;
									else
										myRobot.actionctrl.status &= ~ACTION_BASIC;
									f_close(&lis);
									OSSemPost(ActionSem);
									//在此添加信号量
								}
							}
							break;
						case 13:
							break;
						case 14:
							break;
						case 15:
							break;
						case 16:
							break;
						case 17:
							break;
						case 18:
							break;
						case 19:
							break;
						default:
							break;
					}
					myRobot.ld3320State.state = LD_ASR_NONE;
					break;
				}
				case LD_ASR_FOUNDZERO:
				default:
					myRobot.ld3320State.state = LD_ASR_NONE;
					break;
			}
		}
	}
}
Ejemplo n.º 18
0
static afs_int32
file_WriteLabel(struct butm_tapeInfo *info, struct butm_tapeLabel *label,
		afs_int32 rewind)
{
    afs_int32 code = 0;
    afs_int32 fcode;
    struct tapeLabel *tlabel;
    struct progress *p;
    afs_int64 off;		/* offset */

    if (info->debug)
	printf("butm: Write tape label\n");

    POLL();
    info->error = 0;

    code = check(info, WRITE_OP);
    if (code)
	ERROR_EXIT(code);
    if (!label)
	ERROR_EXIT(BUTM_BADARGUMENT);
    if (label->structVersion != CUR_TAPE_VERSION)
	ERROR_EXIT(BUTM_OLDINTERFACE);

    if (rewind) {		/* Not appending, so rewind */
	code = rewindFile(info);
	if (code)
	    ERROR_EXIT(code);

	if (isafile) {
	    p = (struct progress *)info->tmRock;
	    off = 0;
	    code = USD_IOCTL(p->fid, USD_IOCTL_SETSIZE, &off);
	    if (code)
		ERROR_EXIT(BUTM_POSITION);
	}
    } else {
	if (READS || WRITES)
	    ERROR_EXIT(BUTM_BADOP);
    }

    /* Copy the label into the tape block
     * ---------------------------------- */
    memset(tapeBlock, 0, BUTM_BLOCKSIZE);

    if (!label->creationTime)
	label->creationTime = time(0);

    tlabel = (struct tapeLabel *)tapeBlock;
    memcpy(&tlabel->label, label, sizeof(struct butm_tapeLabel));
    tlabel->label.structVersion = htonl(CUR_TAPE_VERSION);
    tlabel->label.creationTime = htonl(tlabel->label.creationTime);
    tlabel->label.expirationDate = htonl(tlabel->label.expirationDate);
    tlabel->label.size = htonl(tlabel->label.size);
    tlabel->label.useCount = htonl(tlabel->label.useCount);
    tlabel->label.dumpid = htonl(tlabel->label.dumpid);

    /*
     * write the tape label - For appends, the write may need to skip
     * over 1 or 2 EOF marks that were written when tape was closed after
     * the last dump. Plus, some AIX tape drives require we try forwarding
     * over the last EOF and take an error before we can write the new label.
     * ---------------------------------------------------------------------- */
    code = WriteTapeBlock(info, tapeBlock, BUTM_BLOCKSIZE, BLOCK_LABEL);
    if (!isafile && !rewind && (code == BUTM_IO))
	do {			/* do if write failed */
	    fcode = SeekFile(info, 1);	/* skip over the EOF */
	    if (fcode)
		break;		/* leave if error */

	    code =
		WriteTapeBlock(info, tapeBlock, BUTM_BLOCKSIZE, BLOCK_LABEL);
	    if (code != BUTM_IO)
		break;		/* continue if write failed */

	    fcode = SeekFile(info, 1);	/* skip over the EOF */
	    if (fcode) {	/* retry 1 write if couldn't skip */
		code =
		    WriteTapeBlock(info, tapeBlock, BUTM_BLOCKSIZE,
				   BLOCK_LABEL);
		break;
	    }

	    code =
		WriteTapeBlock(info, tapeBlock, BUTM_BLOCKSIZE, BLOCK_LABEL);
	    if (code != BUTM_IO)
		break;		/* continue if write failed */

	    fcode = SeekFile(info, 1);	/* skip over the EOF */
	    if (fcode) {	/* retry 1 write if couldn't skip */
		code =
		    WriteTapeBlock(info, tapeBlock, BUTM_BLOCKSIZE,
				   BLOCK_LABEL);
		break;
	    }
	    break;
	} while (0);

    /* clear the write error status a failed WriteTapeBlock may have produced */
    if (!code)
	info->status &= ~BUTM_STATUS_WRITEERROR;

  error_exit:
    return code;
}