Newsgroup: it.comp.lang.c++
Titolo: Prelevare informazioni dallo stack

Un saluto a tutti.
Ho il seguente quesito: ho una particolare istanza di una classe che 
chiama un metodo. Questo metodo non risiede in quella classe e nel suo 
corpo io avrei bisogno di fare riferimento a quella istanza chiamante, 
quindi mi serve il puntatore all'oggetto che ha chiamato il metodo. Non 
posso passare "this" come argomento perchè non posso modificare il codice.
Mi chiedevo se fosse possibile prelevare tale informazione dallo stack.
Uso il gcc
Grazie
Ciao


Ciao,
Immagino che tu non abbia ricevuto nessuna risposta semplicemente perchè non
è chiaro cosa vuoi fare. Forse dovresti pensare con maggiore attenzione al
tuo problema e quindi esprimerlo meglio.
In ogni caso in C++, per fare operazioni 'legali' o potenzialmente non
pericolose (a meno che tu non stia scrivendo uno shellcode, ad esempio) non
hai nessuna necessità di leggere e/o manipolare direttamente lo stack (che
non è cosa banale e probabilmente in molti casi ti necessita di scrivere
istruzioni Assembly da immettere in-line nel codice C++).
Ripeto: prova a ripensare di cosa hai realmente bisogno ed esprimiti con
maggiore chiarezza.
Buon lavoro,
fabio de francesco
(fabiomdf)
--------------------------------
Inviato via 
http://arianna.libero.it/usenet/

 
Rieccomi.
Sto lavorando con le librerie SystemC (
www.systemc.org
).
Praticamente ho la seguente struttura
   --------            --------
  |        |          |        |
  | modulo|X|--------|Y| canale|
  |        |          |        |
   --------            --------
Il modulo è una classe che dichiara una porta (X in figura) come membro dati
sc_port<myIf> port1 (sc_port è un tipo predefinito di systemc).
Tale porta serve al modulo per comunicare con l'esterno, in questo caso 
per chiamare i metodi dell' interfaccia myIf (Y in figura è 
l'interfaccia) implementati dal canale.
myIf è una classe con metodi virtual puri che mostra quali servizi 
fornisce il canale. Questo eredita da tale classe e fornisce un 
implementazioni a tali metodi.
Quindi quando il modulo fa una chiamata del genere al suo interno
port1->ciao()
sta chiamando il metodo ciao() fornito dal canale.
Questione:
1) devo inserire tra quei due oggetti un terzo oggetto (diciamo un 
bridge) che monitorizzi le chiamate che il modulo fa al canale.
2)il modulo non deve accorgersene (cioè deve continuare a vedere la 
stessa interfaccia che vedeva prima).
3) non posso modificare il codice del modulo.
4) ho l'obbligo di avere all'interno del bridge il metodo di interfaccia
	void ciao(modulo*)
(che va ad inoltrare la chiamata corretta al canale) dove prendo come 
argomento il puntatore all'istanza della classe modulo che fa le 
chiamate (in un caso piu complesso possono esserci istanze diverse di 
modulo che chiamano ciao() quindi devo poter sapere chi chiama tale 
metodo). Questo puntatore è di vitale importanza all'interno del bridge.
La prima idea è stata
port1->ciao(this)
ma violerei il punto 3. Quindi avevo pensato a creare un adapter da 
porre tra il modulo e il bridge che in fase di costruzione ricevesse il 
puntatore all'istanza del modulo.
Esso poi avrebbe ereditato da myIf e definito la ciao() come segue
void adapter::ciao() {
    toBridge->ciao(myMod)
}
in modo da chiamare la ciao(modulo*) del bridge attraverso la porta 
toBridge.
Questa soluzione che va bene in teoria, è poco attuabile nella pratica 
per problemi che non vi sto a spiegare e dovrei evitarla :)
A questo punto non ho piu idee su come passare quel maledetto pointer al 
bridge. L'unica cosa che mi viene in mente è lo stack.
Spero di essere stato chiaro...cmq sto qua per chiarimenti.
Grazie
Ciao :)

Non so se ho capito bene il problema, ma forse puoi
applicare il Design Pattern "Proxy":
Da quanto ho capito:
hai una classe Modulo che accede ai
metodi di una classe Canale (che implementa un interfaccia IF)
e tuo vuoi monitorare gli accessi di Modulo a Canale.
Puoi introdurre una classe Proxy che implementa la stessa interfaccia,
contiene un puntatore alla classe concreta e rigira a questo tutte le
chiamate.
Es.
class Proxy : public myIF {
   Canale* c_;
 public:
   Proxy(Canale* c) : c_(c) {}
   virtual void ciao() {
      std::cout << "ciao called!" << std::endl;
      // aggiungi qui, e in ogni altro metodo virtuale
      // di myIF quello che ti serve
      c_->ciao();
   }
};
A questo punto, basta che passi al Modulo il Proxy invece del Canale.
Il Modulo non si accorgera' della differenza e tu potrai "intercettare"
tutte le chiamate.
Solo non ho capito bene il punto 4.
Spero di esserti stato d'aiuto.
Saluti,
Fabio

 
Grazie mille
Ciao :)