Pagina Principale   Moduli   Lista dei namespaces   Gerarchia delle classi   Lista in ordine alfabetico   Lista dei composti   Lista dei files   Membri dei namespaces   Membri dei composti   Membri dei files   Esempi  

/home/fbassi/devel/projects/reti/Storage/Storage_i.cc

Vai alla documentazione di questo file.
00001 /*
00002  *    FBFS Distributed Object Repository
00003  *    Copyright (C) 2001 Francesco V. Bassi
00004  *
00005  *    This program is free software; you can redistribute it and/or modify
00006  *    it under the terms of the GNU General Public License as published by
00007  *    the Free Software Foundation; either version 2 of the License, or
00008  *    (at your option) any later version.
00009  *
00010  *    This program is distributed in the hope that it will be useful,
00011  *    but WITHOUT ANY WARRANTY; without even the implied warranty of
00012  *    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00013  *    GNU General Public License for more details.
00014  *
00015  *    You should have received a copy of the GNU General Public License
00016  *    along with this program; if not, write to the Free Software
00017  *    Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
00018  */
00019 
00025 #include "Storage_i.h"
00026 
00027 #include "../utils/File.h"
00028 #include "../utils/NameServer.h"
00029 #include "../Object/Object.h"
00030 #include "../idl/Storage.hh"
00031 
00032 #include <dirent.h>
00033 
00034 Storage_i::Storage_i(Prefs &p, const CORBA::ORB_ptr &o) : prefs(p), orb(o) {;
00035     dirname = prefs.get("datadir", "data");
00036     metadirname = prefs.get("metadatadir", dirname);
00037 };
00038     
00039 Obj *Storage_i::get(const Security &cert, const Obj_id &id)
00040                     throw(NotFound, SecurityException, InternalError) {
00041     string ident(id.name);
00042     try {
00043         lock.lock(ident);
00044             string strobj = File::read( ident, dirname );
00045         lock.unlock(ident);
00046         return Object::string2Obj(strobj);
00047     } catch (File::NotFound) {
00048         lock.unlock(ident);
00049         throw NotFound();
00050     } catch (...) {
00051         lock.unlock(ident);
00052         throw InternalError();
00053     };
00054 };
00055 
00056 Obj_ts Storage_i::get_ts(const Security &cert, const Obj_id &id)
00057                     throw(NotFound, SecurityException, InternalError) {
00058     string ident(id.name);
00059     try {
00060         lock.lock(ident);
00061             string strobj = File::read( ident + ".ts", metadirname );
00062         lock.unlock(ident);
00063         return Object::string2Obj_ts(strobj);
00064     } catch (File::NotFound) {
00065         lock.unlock(ident);
00066         throw NotFound();
00067     } catch (...) {
00068         lock.unlock(ident);
00069         throw InternalError();
00070     };
00071 };
00072 
00073 Obj_prop Storage_i::get_prop(const Security &cert, const Obj_id &id)
00074                     throw(NotFound, SecurityException, InternalError) {
00075     string ident(id.name);
00076     try {
00077         lock.lock(ident);
00078             string strobj = File::read( ident + ".prop", metadirname );
00079         lock.unlock(ident);
00080         return Object::string2Obj_prop(strobj);
00081     } catch (File::NotFound) {
00082         lock.unlock(ident);
00083         throw NotFound();
00084     } catch (...) {
00085         lock.unlock(ident);
00086         throw InternalError();
00087     };
00088 };
00089 
00090 void Storage_i::put(const Security &cert, const Obj &obj, const Obj_id &id, const Obj_prop &prop,
00091                     const Obj_ts &ts) throw(AlreadyPresent, SecurityException, InternalError) {
00092     string ident(id.name);
00093     string obj_str = Object::Obj2string(obj);
00094     string obj_ts_str = Object::Obj_ts2string(ts);
00095     string obj_prop_str = Object::Obj_prop2string(prop);
00096 
00097     lock.lock(ident, true);
00098     
00099     // Cerca di scrivere il file. Se c'è già, esci con throw AlreadyPresent().
00100     try {
00101         File::write(obj_str, ident, dirname);
00102     } catch (File::AlreadyPresent) {
00103         lock.unlock(ident);
00104         throw AlreadyPresent();
00105     };
00106 
00107     try {
00108         // Cerca di scrivere i file .ts e .prop cancellando eventualmente le vecchie versioni.
00109         File::write(obj_ts_str, ident+".ts", metadirname, true);
00110         File::write(obj_prop_str, ident+".prop", metadirname, true);
00111     } catch (...) {
00112         // Se durante l'operazione si verifica un errore, cerca di cancellare i file prodotti
00113         // e esci con throw InternalError().
00114         try { File::remove(ident, dirname); } catch (...) {};
00115         try { File::remove(ident+".ts", metadirname); } catch (...) {};
00116         try { File::remove(ident+".prop", metadirname); } catch (...) {};
00117         lock.unlock(ident);
00118         throw InternalError();
00119     };
00120     lock.unlock(ident);
00121 };
00122 
00123 Obj_infoList *Storage_i::list(const Security &cert) throw(SecurityException, InternalError) {
00124     DIR *dir;
00125     struct dirent * entry;
00126     int count=0;
00127     
00128     dir = opendir( metadirname.c_str() );
00129     if(dir == NULL)
00130         throw InternalError();
00131     while( entry=readdir(dir) ) {
00132         string name(entry->d_name);
00133         if(name.find(".ts")==name.length()-3 && name.length()>3 )
00134             count++;
00135     };
00136     free(entry);
00137     closedir(dir);
00138     
00139     Obj_infoList *list = new Obj_infoList(count);
00140     list->length(count);
00141 
00142     dir = opendir( metadirname.c_str() );
00143     if(dir == NULL)
00144         throw InternalError();
00145     int i=0;
00146     while( entry=readdir(dir) ) {
00147         string name(entry->d_name);
00148         if(name.find(".ts")==name.length()-3 && name.length()>3 ) {
00149             name = name.substr(0,name.length()-3);
00150             
00151             Obj_info info;
00152             info.id.name= CORBA::string_dup(name.c_str());
00153             try{ info.ts = Object::string2Obj_ts(File::read(name+".ts", metadirname)); } catch (...) {};
00154             try{ info.prop = Object::string2Obj_prop(File::read(name+".prop", metadirname)); } catch (...) {};
00155             
00156             (*list)[i++] = info;
00157         };
00158     };
00159     free(entry);
00160     closedir(dir);
00161     return list;
00162 };
00163 
00164 void Storage_i::put_from_peer(const Security &cert, const Obj_id &id, const char *peer)
00165                     throw(NotFound, PeerNotAvailable, AlreadyPresent, SecurityException, InternalError) {
00166 
00167     // Accesso esclusivo all'oggetto
00168     string ident(id.name);
00169     lock.lock(ident, true);
00170     
00171     // Indirizzo del server da prelevare
00172     utils::URI uri(peer);
00173 
00174     Storage_var storage;
00175     
00176     try {
00177         // Cerca di ottenere un riferimento al server
00178         CORBA::Object_var stor_obj = utils::NameServer::get_object(orb, uri);
00179         storage = fbfs::Storage::_narrow(stor_obj);
00180     } catch(...) {
00181         lock.unlock(ident);
00182         throw PeerNotAvailable();
00183     };
00184     
00185     Obj *obj;
00186     Obj_ts obj_ts;
00187     Obj_prop obj_prop;
00188     try {
00189         obj = storage->get(cert, id);
00190         obj_ts = storage->get_ts(cert, id);
00191         obj_prop = storage->get_prop(cert, id);
00192     } catch(NotFound) {
00193         lock.unlock(ident);
00194         throw NotFound();
00195     } catch(SecurityException) {
00196         lock.unlock(ident);
00197         throw SecurityException();
00198     } catch(...) {
00199         lock.unlock(ident);
00200         throw PeerNotAvailable();
00201     };
00202     
00203     try{
00204         lock.unlock(ident);
00205         put(cert, *obj, id, obj_prop, obj_ts);
00206     } catch(AlreadyPresent) {
00207         throw AlreadyPresent();
00208     } catch(SecurityException) {
00209         throw SecurityException();
00210     } catch(...) {
00211         throw InternalError();
00212     };
00213 };
00214 
00215 void Storage_i::remove(const Security &cert, const Obj_id &id)
00216                     throw(NotFound, SecurityException, InternalError) {
00217     string ident(id.name);
00218 
00219     // Accesso esclusivo all'oggetto
00220     lock.lock(ident, true);
00221     
00222     bool failed = false;
00223     try {
00224         File::remove(ident, dirname);
00225     } catch (File::NotFound) {
00226         lock.unlock(ident);
00227         throw NotFound();
00228     } catch (...) {
00229         failed = true;
00230     };
00231     try { File::remove(ident+".ts", metadirname); } catch (NotFound) {} catch (...) { failed = true;};
00232     try { File::remove(ident+".prop", metadirname); } catch (NotFound) {} catch (...) { failed = true;};
00233 
00234     lock.unlock(ident);
00235     if(failed)
00236         throw InternalError();
00237 };

Generato il Thu Feb 15 13:24:56 2001 per A Simple Distributed Object Repository with CORBA & C++. da doxygen1.2.3 scritto da Dimitri van Heesch, © 1997-2000