⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 tclmacchan.c

📁 linux系统下的音频通信
💻 C
📖 第 1 页 / 共 3 页
字号:
    if ((mode & TCL_ALWAYS_APPEND) || (mode & TCL_APPEND)) {        if (Tcl_Seek(chan, 0, SEEK_END) < 0) {	    *errorCodePtr = errno = EFAULT;	    Tcl_SetErrno(errno);            Tcl_Close(NULL, chan);            FSClose(fileRef);            ckfree((char *) fileState);            return NULL;        }    }        return chan;}/* *---------------------------------------------------------------------- * * FileBlockMode -- * *	Set blocking or non-blocking mode on channel.  Macintosh files *	can never really be set to blocking or non-blocking modes. *	However, we don't generate an error - we just return success. * * Results: *	0 if successful, errno when failed. * * Side effects: *	Sets the device into blocking or non-blocking mode. * *---------------------------------------------------------------------- */static intFileBlockMode(    ClientData instanceData,		/* Unused. */    int mode)				/* The mode to set. */{    return 0;}/* *---------------------------------------------------------------------- * * FileClose -- * *	Closes the IO channel. * * Results: *	0 if successful, the value of errno if failed. * * Side effects: *	Closes the physical channel * *---------------------------------------------------------------------- */static intFileClose(    ClientData instanceData,	/* Unused. */    Tcl_Interp *interp)		/* Unused. */{    FileState *fileState = (FileState *) instanceData;    int errorCode = 0;    OSErr err;    err = FSClose(fileState->fileRef);    FlushVol(NULL, fileState->volumeRef);    if (err != noErr) {	errorCode = errno = TclMacOSErrorToPosixError(err);	panic("error during file close");    }    ckfree((char *) fileState);    Tcl_SetErrno(errorCode);    return errorCode;}/* *---------------------------------------------------------------------- * * FileInput -- * *	Reads input from the IO channel into the buffer given. Returns *	count of how many bytes were actually read, and an error indication. * * Results: *	A count of how many bytes were read is returned and an error *	indication is returned in an output argument. * * Side effects: *	Reads input from the actual channel. * *---------------------------------------------------------------------- */intFileInput(    ClientData instanceData,	/* Unused. */    char *buffer,				/* Where to store data read. */    int bufSize,				/* How much space is available                                 * in the buffer? */    int *errorCodePtr)			/* Where to store error code. */{    FileState *fileState = (FileState *) instanceData;    OSErr err;    long length = bufSize;    *errorCodePtr = 0;    errno = 0;    err = FSRead(fileState->fileRef, &length, buffer);    if ((err == noErr) || (err == eofErr)) {	return length;    } else {	switch (err) {	    case ioErr:		*errorCodePtr = errno = EIO;	    case afpAccessDenied:		*errorCodePtr = errno = EACCES;	    default:		*errorCodePtr = errno = EINVAL;	}        return -1;	    }    *errorCodePtr = errno;    return -1;}/* *---------------------------------------------------------------------- * * FileOutput-- * *	Writes the given output on the IO channel. Returns count of how *	many characters were actually written, and an error indication. * * Results: *	A count of how many characters were written is returned and an *	error indication is returned in an output argument. * * Side effects: *	Writes output on the actual channel. * *---------------------------------------------------------------------- */static intFileOutput(    ClientData instanceData,		/* Unused. */    char *buffer,			/* The data buffer. */    int toWrite,			/* How many bytes to write? */    int *errorCodePtr)			/* Where to store error code. */{    FileState *fileState = (FileState *) instanceData;    long length = toWrite;    OSErr err;    *errorCodePtr = 0;    errno = 0;        if (fileState->appendMode == true) {	FileSeek(instanceData, 0, SEEK_END, errorCodePtr);	*errorCodePtr = 0;    }        err = FSWrite(fileState->fileRef, &length, buffer);    if (err == noErr) {	err = FlushFile(fileState->fileRef);    } else {	*errorCodePtr = errno = TclMacOSErrorToPosixError(err);	return -1;    }    return length;}/* *---------------------------------------------------------------------- * * FileSeek -- * *	Seeks on an IO channel. Returns the new position. * * Results: *	-1 if failed, the new position if successful. If failed, it *	also sets *errorCodePtr to the error code. * * Side effects: *	Moves the location at which the channel will be accessed in *	future operations. * *---------------------------------------------------------------------- */static intFileSeek(    ClientData instanceData,	/* Unused. */    long offset,				/* Offset to seek to. */    int mode,					/* Relative to where                                 * should we seek? */    int *errorCodePtr)			/* To store error code. */{    FileState *fileState = (FileState *) instanceData;    IOParam pb;    OSErr err;    *errorCodePtr = 0;    pb.ioCompletion = NULL;    pb.ioRefNum = fileState->fileRef;    if (mode == SEEK_SET) {	pb.ioPosMode = fsFromStart;    } else if (mode == SEEK_END) {	pb.ioPosMode = fsFromLEOF;    } else if (mode == SEEK_CUR) {	err = PBGetFPosSync((ParmBlkPtr) &pb);	if (pb.ioResult == noErr) {	    if (offset == 0) {		return pb.ioPosOffset;	    }	    offset += pb.ioPosOffset;	}	pb.ioPosMode = fsFromStart;    }    pb.ioPosOffset = offset;    err = PBSetFPosSync((ParmBlkPtr) &pb);    if (pb.ioResult == noErr){	return pb.ioPosOffset;    } else if (pb.ioResult == eofErr) {	long currentEOF, newEOF;	long buffer, i, length;		err = PBGetEOFSync((ParmBlkPtr) &pb);	currentEOF = (long) pb.ioMisc;	if (mode == SEEK_SET) {	    newEOF = offset;	} else if (mode == SEEK_END) {	    newEOF = offset + currentEOF;	} else if (mode == SEEK_CUR) {	    err = PBGetFPosSync((ParmBlkPtr) &pb);	    newEOF = offset + pb.ioPosOffset;	}		/*	 * Write 0's to the new EOF.	 */	pb.ioPosOffset = 0;	pb.ioPosMode = fsFromLEOF;	err = PBGetFPosSync((ParmBlkPtr) &pb);	length = 1;	buffer = 0;	for (i = 0; i < (newEOF - currentEOF); i++) {	    err = FSWrite(fileState->fileRef, &length, &buffer);	}	err = PBGetFPosSync((ParmBlkPtr) &pb);	if (pb.ioResult == noErr){	    return pb.ioPosOffset;	}    }    *errorCodePtr = errno = TclMacOSErrorToPosixError(err);    return -1;}/* *---------------------------------------------------------------------- * * CommonWatch -- * *	Initialize the notifier to watch handles from this channel. * * Results: *	None. * * Side effects: *	None. * *---------------------------------------------------------------------- */static voidCommonWatch(    ClientData instanceData,		/* The file state. */    int mask)				/* Events of interest; an OR-ed                                         * combination of TCL_READABLE,                                         * TCL_WRITABLE and TCL_EXCEPTION. */{    FileState **nextPtrPtr, *ptr;    FileState *infoPtr = (FileState *) instanceData;    int oldMask = infoPtr->watchMask;    if (!initialized) {	FileInit();    }    infoPtr->watchMask = mask;    if (infoPtr->watchMask) {	if (!oldMask) {	    infoPtr->nextPtr = firstFilePtr;	    firstFilePtr = infoPtr;	}    } else {	if (oldMask) {	    /*	     * Remove the file from the list of watched files.	     */	    for (nextPtrPtr = &firstFilePtr, ptr = *nextPtrPtr;		 ptr != NULL;		 nextPtrPtr = &ptr->nextPtr, ptr = *nextPtrPtr) {		if (infoPtr == ptr) {		    *nextPtrPtr = ptr->nextPtr;		    break;		}	    }	}    }}/* *---------------------------------------------------------------------- * * GetOpenMode -- * * Description: *	Computes a POSIX mode mask from a given string and also sets *	a flag to indicate whether the caller should seek to EOF during *	opening of the file. * * Results: *	On success, returns mode to pass to "open". If an error occurs, the *	returns -1 and if interp is not NULL, sets interp->result to an *	error message. * * Side effects: *	Sets the integer referenced by seekFlagPtr to 1 if the caller *	should seek to EOF during opening the file. * * Special note: *	This code is based on a prototype implementation contributed *	by Mark Diekhans. * *---------------------------------------------------------------------- */static intGetOpenMode(    Tcl_Interp *interp,			/* Interpreter to use for error					 * reporting - may be NULL. */    char *string)			/* Mode string, e.g. "r+" or					 * "RDONLY CREAT". */{    int mode, modeArgc, c, i, gotRW;    char **modeArgv, *flag;    /*     * Check for the simpler fopen-like access modes (e.g. "r").  They     * are distinguished from the POSIX access modes by the presence     * of a lower-case first letter.     */    mode = 0;    if (islower(UCHAR(string[0]))) {	switch (string[0]) {	    case 'r':		mode = TCL_RDONLY;		break;	    case 'w':		mode = TCL_WRONLY|TCL_CREAT|TCL_TRUNC;		break;	    case 'a':		mode = TCL_WRONLY|TCL_CREAT|TCL_APPEND;		break;	    default:		error:                if (interp != (Tcl_Interp *) NULL) {                    Tcl_AppendResult(interp,                            "illegal access mode \"", string, "\"",                            (char *) NULL);                }		return -1;	}	if (string[1] == '+') {	    mode &= ~(TCL_RDONLY|TCL_WRONLY);	    mode |= TCL_RDWR;	    if (string[2] != 0) {		goto error;	    }	} else if (string[1] != 0) {	    goto error;	}        return mode;    }    /*     * The access modes are specified using a list of POSIX modes     * such as TCL_CREAT.     */    if (Tcl_SplitList(interp, string, &modeArgc, &modeArgv) != TCL_OK) {        if (interp != (Tcl_Interp *) NULL) {            Tcl_AddErrorInfo(interp,                    "\n    while processing open access modes \"");            Tcl_AddErrorInfo(interp, string);            Tcl_AddErrorInfo(interp, "\"");        }        return -1;    }        gotRW = 0;    for (i = 0; i < modeArgc; i++) {	flag = modeArgv[i];	c = flag[0];	if ((c == 'R') && (strcmp(flag, "RDONLY") == 0)) {	    mode = (mode & ~TCL_RW_MODES) | TCL_RDONLY;	    gotRW = 1;	} else if ((c == 'W') && (strcmp(flag, "WRONLY") == 0)) {	    mode = (mode & ~TCL_RW_MODES) | TCL_WRONLY;	    gotRW = 1;	} else if ((c == 'R') && (strcmp(flag, "RDWR") == 0)) {	    mode = (mode & ~TCL_RW_MODES) | TCL_RDWR;	    gotRW = 1;	} else if ((c == 'A') && (strcmp(flag, "APPEND") == 0)) {	    mode |= TCL_ALWAYS_APPEND;	} else if ((c == 'C') && (strcmp(flag, "CREAT") == 0)) {	    mode |= TCL_CREAT;	} else if ((c == 'E') && (strcmp(flag, "EXCL") == 0)) {	    mode |= TCL_EXCL;	} else if ((c == 'N') && (strcmp(flag, "NOCTTY") == 0)) {	    mode |= TCL_NOCTTY;	} else if ((c == 'N') && (strcmp(flag, "NONBLOCK") == 0)) {	    mode |= TCL_NONBLOCK;	} else if ((c == 'T') && (strcmp(flag, "TRUNC") == 0)) {	    mode |= TCL_TRUNC;	} else {            if (interp != (Tcl_Interp *) NULL) {                Tcl_AppendResult(interp, "invalid access mode \"", flag,                        "\": must be RDONLY, WRONLY, RDWR, APPEND, CREAT",                        " EXCL, NOCTTY, NONBLOCK, or TRUNC", (char *) NULL);            }	    ckfree((char *) modeArgv);	    return -1;	}    }    ckfree((char *) modeArgv);    if (!gotRW) {        if (interp != (Tcl_Interp *) NULL) {            Tcl_AppendResult(interp, "access mode must include either",                    " RDONLY, WRONLY, or RDWR", (char *) NULL);        }	return -1;    }    return mode;}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -