/*************************************************************************** $RCSfile: ctfstoolold.cpp,v $ ------------------- cvs : $Id: ctfstoolold.cpp,v 1.2 2003/02/09 01:59:23 aquamaniac Exp $ begin : Mon Apr 22 2002 copyright : (C) 2002 by Martin Preuss email : martin@libchipcard.de **************************************************************************** * This program is free software; you can redistribute it and/or modify * * it under the terms of the GNU General Public License as published by * * the Free Software Foundation; either version 2 of the License, or * * (at your option) any later version. * * * * This program is distributed in the hope that it will be useful, * * but WITHOUT ANY WARRANTY; without even the implied warranty of * * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * * GNU General Public License for more details. * * * * You should have received a copy of the GNU General Public License * * along with this program; if not, write to the Free Software * * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA * ****************************************************************************/ /* Changes 2002/06/01: Martin Preuss ------------------------------------------------ - improved command line arguments handling - added usage info */ #include #include #include #include #include "ctfilesystem.h" #define k_BLOCKSIZE 2048 #define k_PRG "ctfstool" #define k_PRG_VERSION_INFO \ "ctfstool v0.2 (part of libchipcard v"k_CHIPCARD_VERSION_STRING")\n"\ "(c) 2002 Martin Preuss\n"\ "This program is free software licensed under GPL.\n"\ "See COPYING for details.\n" void usage() { fprintf(stdout, "CTFSTool - A tool to manipulate files on a CTFileOldSystem hosted\n" " by a memory chip card.\n" "(c) 2002 Martin Preuss\n" "This library is free software; you can redistribute it and/or\n" "modify it under the terms of the GNU Lesser General Public\n" "License as published by the Free Software Foundation; either\n" "version 2.1 of the License, or (at your option) any later version.\n" "\n" "Usage:\n" k_PRG" COMMAND [ARGS] [-u USERNAME] [-p PASSWD] [-t TERMINAL]\n" k_PRG" format SIZE NAME - format medium with SIZE bytes and\n" " given NAME\n" k_PRG" scratch SIZE - overwrite SIZE bytes on the card\n" k_PRG" info - show statistical info about the card\n" k_PRG" dump - show all blocks on the card (dump)\n" k_PRG" mode RW | RO - (re)set cards readonly mode\n" k_PRG" ls DIR - show content of given dir on the card\n" k_PRG" rm PATH - remove file/empty folder PATH from the card\n" k_PRG" cat FILE - dump content of the given file on the card\n" " to stdout\n" k_PRG" read SRC DST - read a file from the card and store\n" " it locally\n" "\nOptions:\n" " -u USER - use USER for authentification\n" " -p PASS - use PASS for authentification\n" " -t TERMINAL - short name of the terminal to use (see\n" " man 5 libchipcard.conf)\n" " If omitted then the default terminal will be used.\n" " -h - show this help\n" " -V - show version information\n" ); } struct s_args { string username; string password; string terminal; list params; }; int checkArgs(s_args &args, int argc, char **argv) { int i; string tmp; i=1; while (i=argc) return 1; args.username=argv[i]; } else if (tmp=="-p") { i++; if (i>=argc) return 1; args.password=argv[i]; } else if (tmp=="-t") { i++; if (i>=argc) return 1; args.terminal=argv[i]; } else if (tmp=="-h" || tmp=="--help") { usage(); return -1; } else if (tmp=="-V" || tmp=="--version") { fprintf(stdout,k_PRG_VERSION_INFO); return -1; } else // otherwise add param args.params.push_back(tmp); i++; } // while // that's it return 0; } int formatMedium(s_args args){ CTPointer cardfs; CTPointer cib; int msize; string name; CTError err; if (args.params.size()!=2) { usage(); return 1; } sscanf(args.params.front().c_str(),"%i",&msize); if (!msize) { fprintf(stderr,"Bad size (%d).\n",msize); return 1; } name=args.params.back();; cardfs=new CTCardMedium(args.terminal); try { err=cardfs.ref().formatMedium(name,msize, args.username, args.password); if (!err.isOk()) { fprintf(stderr,"Error: %s\n",err.errorString().c_str()); cardfs.ref().purge(); cardfs.ref().unmount(); return 3; } } // try catch (CTError xerr) { fprintf(stderr,"Exception: %s\n",xerr.errorString().c_str()); cardfs.ref().purge(); cardfs.ref().unmount(); return 3; } return 0; } int makeDirectory(s_args args){ CTPointer cardfs; CTPointer dir; string fname; CTError err; if (args.params.size()!=1) { usage(); return 1; } fname=args.params.front(); cardfs=new CTCardMedium(args.terminal); dir=new CTDirectoryOld(cardfs.ptr(),fname); try { err=cardfs.ref().mount(); if (!err.isOk()) throw err; if (cardfs.ref().isCrypted()) if (!cardfs.ref().authorize(args.username, args.password)) { fprintf(stderr,"You are not authorized.\n"); cardfs.ref().unmount(); return 2; } dir.ref().createDirectory(); dir.ref().closeDirectory(); cardfs.ref().unmount(); } // try catch (CTError xerr) { fprintf(stderr,"Exception: %s\n",xerr.errorString().c_str()); cardfs.ref().purge(); cardfs.ref().unmount(); return 2; } return 0; } int catFile(s_args args){ CTPointer cardfs; CTPointer file; string fname; string d; CTError err; if (args.params.size()!=1) { usage(); return 1; } fname=args.params.front(); cardfs=new CTCardMedium(args.terminal); file=new CTFileOld(cardfs.ptr(),fname); try { err=cardfs.ref().mount(); if (!err.isOk()) throw err; if (cardfs.ref().isCrypted()) if (!cardfs.ref().authorize(args.username, args.password)) { fprintf(stderr,"You are not authorized.\n"); cardfs.ref().unmount(); return 2; } file.ref().openFile(); file.ref().read(d,file.ref().fileInfoBlock().ref().fileSize()); fwrite(d.data(),1,d.length(),stdout); file.ref().closeFile(); cardfs.ref().unmount(); } // try catch (CTError xerr) { fprintf(stderr,"Exception: %s\n",xerr.errorString().c_str()); cardfs.ref().purge(); cardfs.ref().unmount(); return 2; } return 0; } int dumpBlocks(s_args args){ CTPointer cardfs; CTError err; cardfs=new CTCardMedium(args.terminal); try { err=cardfs.ref().mount(); if (!err.isOk()) throw err; if (cardfs.ref().isCrypted()) if (!cardfs.ref().authorize(args.username, args.password)) { fprintf(stderr,"You are not authorized.\n"); cardfs.ref().unmount(); return 2; } cardfs.ref().dumpBlocks(); cardfs.ref().unmount(); } // try catch (CTError xerr) { fprintf(stderr,"Exception: %s\n",xerr.errorString().c_str()); cardfs.ref().purge(); cardfs.ref().unmount(); return 2; } return 0; } int setMode(s_args args){ CTPointer cardfs; CTError err; string ar; bool ro; if (args.params.size()!=1) { usage(); return 1; } ar=args.params.front(); ro=false; if (ar=="RO" || ar=="ro") ro=true; else if (ar=="RW" || ar=="rw") ro=false; else { fprintf(stderr,"unknown mode.\n"); return 1; } cardfs=new CTCardMedium(args.terminal); try { err=cardfs.ref().mount(); if (!err.isOk()) throw err; cardfs.ref().setReadOnly(ro); cardfs.ref().unmount(); } // try catch (CTError xerr) { fprintf(stderr,"Exception: %s\n",xerr.errorString().c_str()); cardfs.ref().purge(); cardfs.ref().unmount(); return 2; } return 0; } int remove(s_args args){ CTPointer cardfs; CTPointer file; string fname; string d; CTError err; if (args.params.size()!=1) { usage(); return 1; } fname=args.params.front(); cardfs=new CTCardMedium(args.terminal); file=new CTFileOld(cardfs.ptr(),fname); try { err=cardfs.ref().mount(); if (!err.isOk()) throw err; if (cardfs.ref().isCrypted()) if (!cardfs.ref().authorize(args.username, args.password)) { fprintf(stderr,"You are not authorized.\n"); cardfs.ref().unmount(); return 2; } file.ref().removeFile(); cardfs.ref().unmount(); } // try catch (CTError xerr) { fprintf(stderr,"Exception: %s\n",xerr.errorString().c_str()); cardfs.ref().purge(); cardfs.ref().unmount(); return 2; } return 0; } int lsDirectory(s_args args){ CTPointer cardfs; CTPointer dir; CTPointer fib; string fname; string tmp; CTError err; char acc[11]; if (args.params.size()!=1) { usage(); return 1; } fname=args.params.front(); acc[3]='-'; acc[6]='-'; acc[9]='-'; acc[10]=0; cardfs=new CTCardMedium(args.terminal); try { err=cardfs.ref().mount(); if (!err.isOk()) throw err; if (cardfs.ref().isCrypted()) if (!cardfs.ref().authorize(args.username, args.password)) { fprintf(stderr,"You are not authorized.\n"); cardfs.ref().unmount(); return 2; } dir=new CTDirectoryOld(cardfs.ptr(),fname); dir.ref().openDirectory(); // read dir do { fib=dir.ref().readEntry(); if (fib.isValid()) { // create access if (fib.ref().attributes() & k_CTFS_FILEINFO_ATT_DIR) acc[0]='d'; else acc[0]='-'; if (fib.ref().attributes() & k_CTFS_FILEINFO_ATT_READ) acc[1]='r'; else acc[1]='-'; if (fib.ref().attributes() & k_CTFS_FILEINFO_ATT_WRITE) acc[2]='w'; else acc[2]='-'; acc[4]=acc[1]; acc[7]=acc[1]; acc[5]=acc[2]; acc[8]=acc[2]; fprintf(stdout,"%s %5d %s\n", acc, fib.ref().fileSize(), fib.ref().fileName().c_str()); } } while(fib.isValid()); dir.ref().closeDirectory(); cardfs.ref().unmount(); } // try catch (CTError xerr) { fprintf(stderr,"Exception: %s\n",xerr.errorString().c_str()); cardfs.ref().purge(); cardfs.ref().unmount(); return 2; } return 0; } int writeToCard(s_args args){ CTPointer cardfs; CTPointer cf; string sname; string dname; FILE *sf; char buffer[k_BLOCKSIZE]; int i; string tmp; CTError err; if (args.params.size()!=2) { usage(); return 1; } sname=args.params.front(); dname=args.params.back(); // try to open the source file sf=fopen(sname.c_str(),"r"); if (!sf) { fprintf(stderr,"Could not open %s (%s)\n", sname.c_str(),strerror(errno)); return 2; } cardfs=new CTCardMedium(args.terminal); cf=new CTFileOld(cardfs.ptr(),dname); try { err=cardfs.ref().mount(); if (!err.isOk()) throw err; if (cardfs.ref().isCrypted()) if (!cardfs.ref().authorize(args.username, args.password)) { fprintf(stderr,"You are not authorized.\n"); cardfs.ref().unmount(); return 2; } cf.ref().createFile(true); // actually copy file while (!feof(sf)) { // read from file i=fread(buffer,1,sizeof(buffer),sf); if (i<1) break; tmp.assign(buffer,i); // write to card cf.ref().write(tmp); } cf.ref().closeFile(); // remove destination file on read error if (ferror(sf)) { fprintf(stderr,"Error reading from %s (%s)\n", sname.c_str(),strerror(errno)); //cf.ref().removeFile(); cardfs.ref().purge(); cardfs.ref().unmount(); return 3; } //cardfs.ref().purge(); // DEBUG cardfs.ref().unmount(); } // try catch (CTError xerr) { fprintf(stderr,"Exception: %s\n",xerr.errorString().c_str()); cardfs.ref().purge(); cardfs.ref().unmount(); return 3; } if (fclose(sf)) { fprintf(stderr,"Could not close %s (%s)\n", sname.c_str(),strerror(errno)); return 2; } return 0; } int readFromCard(s_args args){ CTPointer cardfs; CTPointer cf; string sname; string dname; FILE *sf; int i; string tmp; CTError err; if (args.params.size()!=2) { usage(); return 1; } sname=args.params.front(); dname=args.params.back(); // try to open the source file sf=fopen(dname.c_str(),"w+"); if (!sf) { fprintf(stderr,"Could not open %s (%s)\n", dname.c_str(),strerror(errno)); return 2; } cardfs=new CTCardMedium(args.terminal); cf=new CTFileOld(cardfs.ptr(),sname); try { err=cardfs.ref().mount(); if (!err.isOk()) throw err; if (cardfs.ref().isCrypted()) if (!cardfs.ref().authorize(args.username, args.password)) { fprintf(stderr,"You are not authorized.\n"); cardfs.ref().unmount(); return 2; } cf.ref().openFile(); // actually copy file while(1) { cf.ref().read(tmp,k_BLOCKSIZE); if (tmp.length()==0) break; i=fwrite(tmp.data(),1,tmp.length(),sf); if (i!=(int)tmp.length()) { fprintf(stderr,"Error writing to %s (%s)\n", dname.c_str(),strerror(errno)); } } // while cf.ref().closeFile(); cardfs.ref().unmount(); } // try catch (CTError xerr) { fprintf(stderr,"Exception: %s\n",xerr.errorString().c_str()); cardfs.ref().purge(); cardfs.ref().unmount(); return 3; } if (fclose(sf)) { fprintf(stderr,"Could not close %s (%s)\n", sname.c_str(),strerror(errno)); return 2; } return 0; } int info(s_args args) { CTPointer cardfs; CTPointer mib; string fname; string d; unsigned int fblocks, fbytes, ublocks, ubytes; string label; float fl; CTError err; if (args.params.size()!=0) { usage(); return 1; } cardfs=new CTCardMedium(args.terminal); try { // mount the card err=cardfs.ref().mount(); if (!err.isOk()) throw err; if (cardfs.ref().isCrypted()) if (!cardfs.ref().authorize(args.username, args.password)) { fprintf(stderr,"You are not authorized.\n"); cardfs.ref().unmount(); return 2; } // retrieve and show some info label=cardfs.ref().label(); cardfs.ref().usageStats(fblocks,fbytes,ublocks,ubytes); mib=cardfs.ref().mediumInfoBlock(); printf("General information\n"); printf("------------------------------------------------------\n"); printf("Card Name : %s\n",label.c_str()); printf("Card Size : %6d byte(s)\n",mib.ref().mediumSize()); printf("Used Bytes : %6d byte(s) in %d block(s)\n",ubytes,ublocks); printf("Free Bytes : %6d byte(s) in %d block(s)\n",fbytes,fblocks); if (mib.ref().flags()&k_CTFS_MEDIUMINFO_FLAG_RO) printf("Medium is write protected\n"); else printf("Medium is not write protected\n"); if (mib.ref().flags()&k_CTFS_MEDIUMINFO_FLAG_CRYPT) printf("Medium is encrypted\n"); else printf("Medium is not encrypted\n"); printf("\n"); printf("Statistical information\n"); printf("------------------------------------------------------\n"); if (ublocks) printf("Bytes per used block : %6d byte(s)\n", ubytes/ublocks); if (fblocks) printf("Bytes per free block : %6d byte(s)\n", fbytes/fblocks); if (fblocks && ublocks) { printf("Bytes per block : %6d byte(s)\n", (fbytes+ubytes)/(fblocks+ublocks)); fl=((float)(ublocks+fblocks)*k_CTFS_HEADER_LENGTH)/ ((mib.ref().mediumSize()/100.0)); printf("Block overhead : %6.2f%% (%d bytes)\n",fl, (ublocks+fblocks)*k_CTFS_HEADER_LENGTH); fl=((float)(mib.ref().mediumSize()-fbytes-ubytes)/ ((mib.ref().mediumSize()/100.0))); printf("Total overhead : %6.2f%% (%d bytes)\n",fl, mib.ref().mediumSize()-fbytes-ubytes); } // unmount medium cardfs.ref().unmount(); } // try catch (CTError xerr) { fprintf(stderr,"Exception: %s\n",xerr.errorString().c_str()); cardfs.ref().purge(); cardfs.ref().unmount(); return 2; } return 0; } int scratchMedium(s_args args){ CTPointer cardfs; int s; CTError err; if (args.params.size()!=1) { usage(); return 1; } sscanf(args.params.front().c_str(),"%i",&s); if (!s) { fprintf(stderr,"Bad size (%d).\n",s); return 1; } cardfs=new CTCardMedium(args.terminal); try { cardfs.ref().scratchMedium(s); } // try catch (CTError xerr) { fprintf(stderr,"Exception: %s\n",xerr.errorString().c_str()); cardfs.ref().purge(); cardfs.ref().unmount(); return 2; } return 0; } int main(int argc, char **argv) { libChipCard libcc; string cmd; s_args args; int rv; fprintf(stderr, "\n--------------------------------------------------------\n" "WARNING: This tool uses the deprecated file system.\n" "For this reason it is from now on unable to store files\n" "on the card.\n" "However, you can use it to READ your files off the card\n" "to port your files stored on an old file system to the\n" "new file system.\n" "--------------------------------------------------------\n\n"); rv=checkArgs(args,argc,argv); if (rv==-1) return 0; else if (rv) return rv; if (argc<2) { usage(); return 1; } if (args.params.empty()) { usage(); return 1; } cmd=args.params.front(); args.params.pop_front(); if (cmd=="format") return formatMedium(args); else if (cmd=="scratch") return scratchMedium(args); //else if (cmd=="md") // return makeDirectory(args); else if (cmd=="ls") return lsDirectory(args); else if (cmd=="cat") return catFile(args); else if (cmd=="info") return info(args); //else if (cmd=="write") // return writeToCard(args); else if (cmd=="read") return readFromCard(args); else if (cmd=="rm") return remove(args); else if (cmd=="dump") return dumpBlocks(args); else if (cmd=="mode") return setMode(args); else { fprintf(stderr,"Unknown command.\n"); usage(); return 1; } }