From a4c804b49ec872b71bd5a0167c3ad45704a3cc30 Mon Sep 17 00:00:00 2001 From: adiblol Date: Thu, 8 Mar 2012 19:32:05 +0100 Subject: Initial commit, Copyright (C) 2001-2008, Daniel ROUX & EPSITEC SA, www.epsitec.ch --- src/CBot/ClassFILE.cpp | 412 +++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 412 insertions(+) create mode 100644 src/CBot/ClassFILE.cpp (limited to 'src/CBot/ClassFILE.cpp') diff --git a/src/CBot/ClassFILE.cpp b/src/CBot/ClassFILE.cpp new file mode 100644 index 0000000..21bd39e --- /dev/null +++ b/src/CBot/ClassFILE.cpp @@ -0,0 +1,412 @@ +// ClassFile.cpp +// +// définition des méthodes pour la classe FILE + + + +// Variables statiques + +static CBotClass* m_pClassFILE; +static CBotProgram* m_pFuncFile; +static int m_CompteurFileOpen = 0; + + + +// Prépare un nom de fichier. + +void PrepareFilename(CBotString &filename) //DD! +{ + int pos; + + pos = filename.ReverseFind('\\'); + if ( pos > 0 ) + { + filename = filename.Mid(pos+1); // enlève les dossiers + } + + pos = filename.ReverseFind('/'); + if ( pos > 0 ) + { + filename = filename.Mid(pos+1); // aussi ceux avec / + } + + pos = filename.ReverseFind(':'); + if ( pos > 0 ) + { + filename = filename.Mid(pos+1); // enlève aussi la lettre d'unité C: + } + + filename = CBotString("files\\") + filename; +} + + +// constructeur de la classe +// reçois le nom du fichier en paramètre + +// exécution +BOOL rfconstruct (CBotVar* pThis, CBotVar* pVar, CBotVar* pResult, int& Exception) +{ + CBotString mode; + + // accepte sans paramètre + if ( pVar == NULL ) return TRUE; + + // qui doit être une chaîne de caractères + if ( pVar->GivType() != CBotTypString ) { Exception = CBotErrBadString; return FALSE; } + + CBotString filename = pVar->GivValString(); + PrepareFilename(filename); //DR + + // il peut y avoir un second paramètre + pVar = pVar->GivNext(); + if ( pVar != NULL ) + { + // récupère le mode + mode = pVar->GivValString(); + if ( mode != "r" && mode != "w" ) { Exception = CBotErrBadParam; return FALSE; } + + // pas de 3e paramètre + if ( pVar->GivNext() != NULL ) { Exception = CBotErrOverParam; return FALSE; } + } + + // enregistre le nom du fichier + pVar = pThis->GivItem("filename"); + pVar->SetValString(filename); + + if ( ! mode.IsEmpty() ) + { + // ouvre le ficher demandé + FILE* pFile = fopen( filename, mode ); + if ( pFile == NULL ) { Exception = CBotErrFileOpen; return FALSE; } + + m_CompteurFileOpen ++; + + // enregiste le canal du fichier + pVar = pThis->GivItem("handle"); + pVar->SetValInt((long)pFile); + } + + return TRUE; +} + +// compilation +CBotTypResult cfconstruct (CBotVar* pThis, CBotVar* &pVar) +{ + // accepte sans paramètre + if ( pVar == NULL ) return CBotTypResult( 0 ); + + // qui doit être une chaine + if ( pVar->GivType() != CBotTypString ) + return CBotTypResult( CBotErrBadString ); + + // il peut y avoir un second paramètre + pVar = pVar->GivNext(); + if ( pVar != NULL ) + { + // qui doit être une chaine + if ( pVar->GivType() != CBotTypString ) + return CBotTypResult( CBotErrBadString ); + // pas de 3e paramètre + if ( pVar->GivNext() != NULL ) return CBotTypResult( CBotErrOverParam ); + } + + // le résultat est de type void (constructeur) + return CBotTypResult( 0 ); +} + + +// destructeur de la classe + +// exécution +BOOL rfdestruct (CBotVar* pThis, CBotVar* pVar, CBotVar* pResult, int& Exception) +{ + // récupère l'élément "handle" + pVar = pThis->GivItem("handle"); + + // pas ouvert ? pas de problème + if ( pVar->GivInit() != IS_DEF) return TRUE; + + FILE* pFile= (FILE*)pVar->GivValInt(); + fclose(pFile); + m_CompteurFileOpen --; + + pVar->SetInit(IS_NAN); + + return TRUE; +} + + +// méthode FILE :: open +// reçois le mode r/w en paramètre + +// exécution +BOOL rfopen (CBotVar* pThis, CBotVar* pVar, CBotVar* pResult, int& Exception) +{ + // il doit y avoir un paramètre + if ( pVar == NULL ) { Exception = CBotErrLowParam; return FALSE; } + + // qui doit être une chaîne de caractères + if ( pVar->GivType() != CBotTypString ) { Exception = CBotErrBadString; return FALSE; } + + // il peut y avoir un second paramètre + if ( pVar->GivNext() != NULL ) + { + // dans ce cas le premier paramètre est le nom du fichier + CBotString filename = pVar->GivValString(); + PrepareFilename(filename); //DR + + // enregistre le nom du fichier + CBotVar* pVar2 = pThis->GivItem("filename"); + pVar2->SetValString(filename); + + // paramètre suivant est le mode + pVar = pVar -> GivNext(); + } + + CBotString mode = pVar->GivValString(); + if ( mode != "r" && mode != "w" ) { Exception = CBotErrBadParam; return FALSE; } + + // pas de 3e paramètre + if ( pVar->GivNext() != NULL ) { Exception = CBotErrOverParam; return FALSE; } + + // récupère l'élément "handle" + pVar = pThis->GivItem("handle"); + + // qui doit pas être initialisé + if ( pVar->GivInit() == IS_DEF) { Exception = CBotErrFileOpen; return FALSE; } + + // reprend le nom du fichier + pVar = pThis->GivItem("filename"); + CBotString filename = pVar->GivValString(); + + PrepareFilename(filename); //DD! (si le nom a été attribué par h.filename = "..."; + + // ouvre le ficher demandé + FILE* pFile = fopen( filename, mode ); + if ( pFile == NULL ) //DR + { + pResult->SetValInt(FALSE); //DR + return TRUE; //DR + } + + m_CompteurFileOpen ++; + + // enregiste le canal du fichier + pVar = pThis->GivItem("handle"); + pVar->SetValInt((long)pFile); + + pResult->SetValInt(TRUE); //DR + return TRUE; +} + +// compilation +CBotTypResult cfopen (CBotVar* pThis, CBotVar* &pVar) +{ + // il doit y avoir un paramètre + if ( pVar == NULL ) return CBotTypResult( CBotErrLowParam ); + + // qui doit être une chaine + if ( pVar->GivType() != CBotTypString ) + return CBotTypResult( CBotErrBadString ); + + // il peut y avoir un second paramètre + pVar = pVar->GivNext(); + if ( pVar != NULL ) + { + // qui doit être une chaine + if ( pVar->GivType() != CBotTypString ) + return CBotTypResult( CBotErrBadString ); + + // pas de 3e paramètre + if ( pVar->GivNext() != NULL ) return CBotTypResult( CBotErrOverParam ); + } + + // le résultat est de type bool + return CBotTypResult(CBotTypBoolean); //DR +} + + +// méthode FILE :: close + +// exécution +BOOL rfclose (CBotVar* pThis, CBotVar* pVar, CBotVar* pResult, int& Exception) +{ + // il ne doit pas y avoir de paramètre + if ( pVar != NULL ) return CBotErrOverParam; + + // récupère l'élément "handle" + pVar = pThis->GivItem("handle"); + + if ( pVar->GivInit() != IS_DEF) { Exception = CBotErrNotOpen; return FALSE; } + + FILE* pFile= (FILE*)pVar->GivValInt(); + fclose(pFile); + m_CompteurFileOpen --; + + pVar->SetInit(IS_NAN); + + return TRUE; +} + +// compilation +CBotTypResult cfclose (CBotVar* pThis, CBotVar* &pVar) +{ + // il ne doit pas y avoir de paramètre + if ( pVar != NULL ) return CBotTypResult( CBotErrOverParam ); + + // la fonction retourne un résultat "void" + return CBotTypResult( 0 ); +} + +// méthode FILE :: writeln + +// exécution +BOOL rfwrite (CBotVar* pThis, CBotVar* pVar, CBotVar* pResult, int& Exception) +{ + // il doit y avoir un paramètre + if ( pVar == NULL ) { Exception = CBotErrLowParam; return FALSE; } + + // qui doit être une chaîne de caractères + if ( pVar->GivType() != CBotTypString ) { Exception = CBotErrBadString; return FALSE; } + + CBotString param = pVar->GivValString(); + + // récupère l'élément "handle" + pVar = pThis->GivItem("handle"); + + if ( pVar->GivInit() != IS_DEF) { Exception = CBotErrNotOpen; return FALSE; } + + FILE* pFile= (FILE*)pVar->GivValInt(); + + int res = fputs(param+"\n", pFile); + + // en cas d'erreur génère une exception + if ( res < 0 ) { Exception = CBotErrWrite; return FALSE; } + + return TRUE; +} + +// compilation +CBotTypResult cfwrite (CBotVar* pThis, CBotVar* &pVar) +{ + // il doit y avoir un paramètre + if ( pVar == NULL ) return CBotTypResult( CBotErrLowParam ); + + // qui doit être une chaîne de caractères + if ( pVar->GivType() != CBotTypString ) return CBotTypResult( CBotErrBadString ); + + // pas d'autre paramètre + if ( pVar->GivNext() != NULL ) return CBotTypResult( CBotErrOverParam ); + + // la fonction retourne un résultat void + return CBotTypResult( 0 ); +} + +// méthode FILE :: readln + +// exécution +BOOL rfread (CBotVar* pThis, CBotVar* pVar, CBotVar* pResult, int& Exception) +{ + // il ne doit pas y avoir de paramètre + if ( pVar != NULL ) { Exception = CBotErrOverParam; return FALSE; } + + // récupère l'élément "handle" + pVar = pThis->GivItem("handle"); + + if ( pVar->GivInit() != IS_DEF) { Exception = CBotErrNotOpen; return FALSE; } + + FILE* pFile= (FILE*)pVar->GivValInt(); + + char chaine[2000]; + int i; + for ( i = 0 ; i < 2000 ; i++ ) chaine[i] = 0; + + fgets(chaine, 1999, pFile); + + for ( i = 0 ; i < 2000 ; i++ ) if (chaine[i] == '\n') chaine[i] = 0; + + // en cas d'erreur génère une exception + if ( ferror(pFile) ) { Exception = CBotErrRead; return FALSE; } + + pResult->SetValString( chaine ); + + return TRUE; +} + +// compilation +CBotTypResult cfread (CBotVar* pThis, CBotVar* &pVar) +{ + // il ne doit pas y avoir de paramètre + if ( pVar != NULL ) return CBotTypResult( CBotErrOverParam ); + + // la fonction retourne un résultat "string" + return CBotTypResult( CBotTypString ); +} +// méthode FILE :: readln + + +// exécution +BOOL rfeof (CBotVar* pThis, CBotVar* pVar, CBotVar* pResult, int& Exception) +{ + // il ne doit pas y avoir de paramètre + if ( pVar != NULL ) { Exception = CBotErrOverParam; return FALSE; } + + // récupère l'élément "handle" + pVar = pThis->GivItem("handle"); + + if ( pVar->GivInit() != IS_DEF) { Exception = CBotErrNotOpen; return FALSE; } + + FILE* pFile= (FILE*)pVar->GivValInt(); + + pResult->SetValInt( feof( pFile ) ); + + return TRUE; +} + +// compilation +CBotTypResult cfeof (CBotVar* pThis, CBotVar* &pVar) +{ + // il ne doit pas y avoir de paramètre + if ( pVar != NULL ) return CBotTypResult( CBotErrOverParam ); + + // la fonction retourne un résultat booleen + return CBotTypResult( CBotTypBoolean ); +} + + + + + +void InitClassFILE() +{ +// crée une classe pour la gestion des fichiers +// l'utilisation en est la suivante: +// file canal( "NomFichier.txt" ) +// canal.open( "r" ); // ouvre en lecture +// s = canal.readln( ); // lit une ligne +// canal.close(); // referme le fichier + + // crée la classe FILE + m_pClassFILE = new CBotClass("file", NULL); + // ajoute le composant ".filename" + m_pClassFILE->AddItem("filename", CBotTypString); + // ajoute le composant ".handle" + m_pClassFILE->AddItem("handle", CBotTypInt, PR_PRIVATE); + + // défini un constructeur et un destructeur + m_pClassFILE->AddFunction("file", rfconstruct, cfconstruct ); + m_pClassFILE->AddFunction("~file", rfdestruct, NULL ); + + // défini les méthodes associées + m_pClassFILE->AddFunction("open", rfopen, cfopen ); + m_pClassFILE->AddFunction("close", rfclose, cfclose ); + m_pClassFILE->AddFunction("writeln", rfwrite, cfwrite ); + m_pClassFILE->AddFunction("readln", rfread, cfread ); + m_pClassFILE->AddFunction("eof", rfeof, cfeof ); + + m_pFuncFile = new CBotProgram( ); + CBotStringArray ListFonctions; + m_pFuncFile->Compile( "public file openfile(string name, string mode) {return new file(name, mode);}", ListFonctions); + m_pFuncFile->SetIdent(-2); // identificateur spécial pour RestoreState dans cette fonction +} + -- cgit v1.2.3-1-g7c22