📄 tcl_tape.c
字号:
}/* * tapeFWriteCmd * Sends a series of ndmp_tape_write_requests to the NDMP server to * write to tape the data read from the file specified by the * data-file argument. * usage: tape_write data-file ?record-size? * * Parameters: * clientData (input) - connection handle. * interp (input) - Tcl interpreter. * argc (input) - argument count. * argv (input) - argument array. * * Returns: * Tcl error code. */inttapeFWriteCmd(void* clientData, Tcl_Interp* interp, int argc, char* argv[]){ NdmpConnection connection = (NdmpConnection)clientData; ndmp_tape_write_request request; ndmp_tape_write_reply* reply = 0; static char buf[64512]; struct stat sp; int fd; int r; u_long n; u_long record_size; if (argc < 2 || argc > 3) { Tcl_SetResult(interp, "usage: tape_fwrite data-file ?record-size?", TCL_STATIC); return(TCL_ERROR); } if (argc == 3) { record_size = strtoul(argv[2], 0, 0); if (record_size > sizeof(buf)) { Tcl_SetResult(interp, "invalid record-size", TCL_STATIC); return(TCL_ERROR); } } else record_size = sizeof(buf); memset((void*)&sp, 0, sizeof sp); if (stat(argv[1], &sp) == -1) { Error(LOG_ERR, "Can't get status for file '%s': %s", strerror(errno), argv[1]); return(TCL_ERROR); } if ((fd = open(argv[1], O_RDONLY)) == -1) { Error(LOG_ERR, "Can't open file '%s': %s", argv[1], strerror(errno)); return(TCL_ERROR); } while (sp.st_size) { if ((u_long)sp.st_size > record_size) n = record_size; else n = sp.st_size; sp.st_size -= n; r = read(fd, buf, n); if (r != (int)n) { Error(LOG_ERR, "Error reading the input file (%s): %s\n", argv[1], strerror(errno)); close(fd); return(TCL_ERROR); } request.data_out.data_out_val = buf; request.data_out.data_out_len = n; r = ndmpSendRequest(connection, NDMP_TAPE_WRITE, NDMP_NO_ERR, (void*)&request, (void**)&reply); if (ndmpcCheckNdmpSend(interp, r, reply ? reply->error : 0)) { ndmpFreeMessage(connection); close(fd); return(r < 0 ? TCL_ERROR : TCL_OK); } /* * The reply may be larger than n since the data is padded out * to a full record and the total number of bytes written is * returned. */ if (reply->count < n) { Error(LOG_ERR, "%d bytes written; expected %d\n", reply->count, n); ndmpFreeMessage(connection); close(fd); return(TCL_ERROR); } ndmpFreeMessage(connection); } close(fd); return(TCL_OK);}/* * tapeReadCmd * Sends an ndmp_tape_read_request to the NDMP server. * usage: tape_read length * * Parameters: * clientData (input) - connection handle. * interp (input) - Tcl interpreter. * argc (input) - argument count. * argv (input) - argument array. * * Returns: * Tcl error code. */inttapeReadCmd(void* clientData, Tcl_Interp* interp, int argc, char* argv[]){ NdmpConnection connection = (NdmpConnection)clientData; ndmp_tape_read_request request; ndmp_tape_read_reply* reply = 0; char buf[1024]; int r; if (argc != 2) { Tcl_SetResult(interp, "usage: tape_read length", TCL_STATIC); return(TCL_ERROR); } request.count = strtoul(argv[1], 0, 0); r = ndmpSendRequest(connection, NDMP_TAPE_READ, NDMP_NO_ERR, (void*)&request, (void**)&reply); if (ndmpcCheckNdmpSend(interp, r, reply ? reply->error : 0)) { ndmpFreeMessage(connection); return(r < 0 ? TCL_ERROR : TCL_OK); } sprintf(buf, "%u", reply->data_in.data_in_len); ndmpcTclAddToResult(interp, "length", buf); /* Return a max of 80 characters. */ if (reply->data_in.data_in_len > 80) reply->data_in.data_in_val[80] = '\0'; else reply->data_in.data_in_val[reply->data_in.data_in_len] = '\0'; ndmpcTclAddToResult(interp, "data", reply->data_in.data_in_len != 0 ? reply->data_in.data_in_val : ""); ndmpFreeMessage(connection); return(TCL_OK);} /* * tapeFReadCmd * Sends a series of ndmp_tape_read_requests to the NDMP server to * read tape data that is written to the file specified by the * data-file argument. * usage: tape_read data-file ?record-size? * * Parameters: * clientData (input) - connection handle. * interp (input) - Tcl interpreter. * argc (input) - argument count. * argv (input) - argument array. * * Returns: * Tcl error code. */inttapeFReadCmd(void* clientData, Tcl_Interp* interp, int argc, char* argv[]){ NdmpConnection connection = (NdmpConnection)clientData; ndmp_tape_read_request request; ndmp_tape_read_reply* reply = 0; int fd; int r; if (argc < 2 || argc > 3) { Tcl_SetResult(interp, "usage: tape_fread data-file ?record-size?", TCL_STATIC); return(TCL_ERROR); } if (argc == 3) request.count = strtoul(argv[2], 0, 0); else request.count = 64512; if ((fd = open(argv[1], O_WRONLY|O_CREAT, 0755)) == -1) { Error(LOG_ERR, "Can't open file '%s' to write: %s", argv[1], strerror(errno)); return(TCL_ERROR); } for (;;) { r = ndmpSendRequest(connection, NDMP_TAPE_READ, NDMP_NO_ERR, (void*)&request, (void**)&reply); if (ndmpcCheckNdmpSend(interp, r, reply ? reply->error : 0)) { ndmpFreeMessage(connection); close(fd); return(r < 0 ? TCL_ERROR : TCL_OK); } if (write(fd, reply->data_in.data_in_val, reply->data_in.data_in_len) != (int)reply->data_in.data_in_len) { Error(LOG_ERR, "Error writing the output file (%s): %s", argv[1], strerror(errno)); close(fd); return(TCL_ERROR); } ndmpFreeMessage(connection); } close(fd); return(TCL_OK);}/* * tapeExecuteCdbCmd * Sends an ndmp_tape_execute_cdb_request to the NDMP server. * usage: tape_execute_cdb flags timeout alloc-len cdb-index * Predefined CDBs are defined in cdb.c. * * Parameters: * clientData (input) - connection handle. * interp (input) - Tcl interpreter. * argc (input) - argument count. * argv (input) - argument array. * * Returns: * Tcl error code. */inttapeExecuteCdbCmd(void* clientData, Tcl_Interp* interp, int argc, char* argv[]){ NdmpConnection connection = (NdmpConnection)clientData; ndmp_tape_execute_cdb_request request; ndmp_tape_execute_cdb_reply* reply = 0; int r; if (argc != 5) { Tcl_SetResult(interp, "usage: tape_execute_cdb flags timeout alloc-len cdb-index", TCL_STATIC); return(TCL_ERROR); } request.flags = strtol(argv[1], 0, 0); request.timeout = strtol(argv[2], 0, 0); request.datain_len = strtol(argv[3], 0, 0); if (getCdb(strtol(argv[4], 0, 0), &request.cdb.cdb_val, &request.cdb.cdb_len, &request.dataout.dataout_val, &request.dataout.dataout_len) < 0) { Tcl_SetResult(interp, "undefined cdb-num", TCL_STATIC); return TCL_ERROR; } r = ndmpSendRequest(connection, NDMP_TAPE_EXECUTE_CDB, NDMP_NO_ERR, (void*)&request, (void**)&reply); if (ndmpcCheckNdmpSend(interp, r, reply ? reply->error : 0)) { ndmpFreeMessage(connection); return(r < 0 ? TCL_ERROR : TCL_OK); } displayCdbReply(reply->status, reply->dataout_len, reply->datain.datain_val, reply->datain.datain_len, reply->ext_sense.ext_sense_val, reply->ext_sense.ext_sense_len); ndmpFreeMessage(connection); return(TCL_OK);}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -