Domanda

Esiste un modo per modificare gli assembly .NET esistenti senza ricorrere a strumenti di terze parti? So che PostSharp lo rende possibile, ma trovo incredibilmente dispendioso che lo sviluppatore di PostSharp abbia dovuto sostanzialmente riscrivere la funzionalità dell'intero spazio dei nomi System.Reflection per rendere modificabili gli assembly esistenti.

System.Reflection.Emit consente solo la creazione di nuovi assiemi dinamici. Tuttavia, tutte le classi di builder utilizzate qui ereditano dalle classi di riflessione di base (ad es. TypeBuilder eredita da System.Type ). Sfortunatamente, non sembra esserci un modo per forzare un tipo esistente, caricato dinamicamente in un costruttore di tipi. Almeno, non esiste un modo ufficiale supportato.

E che dire di non supportato? Qualcuno conosce backdoor che consentono di caricare assembly o tipi esistenti in tali classi di builder?

Mente, non sono non alla ricerca di modi per modificare l'assembly corrente (questo potrebbe anche essere una richiesta irragionevole) ma solo per modificare gli assembly esistenti caricati dal disco. Temo che non ci sia nulla di simile, ma vorrei chiedere comunque.

Nel peggiore dei casi, si dovrebbe ricorrere a ildasm.exe per disassemblare il codice e quindi a ilasm.exe per il riassemblaggio, ma non esiste una toolchain (leggi: Lettore IL) contenuto in .NET per lavorare con i dati IL (o c'è?).

/ EDIT:

Non ho un caso d'uso specifico. Sono solo interessato a una soluzione di uso generale perché l'applicazione di patch agli assembly esistenti è un'attività abbastanza comune. Prendiamo ad esempio gli offuscatori, o i profiler o le librerie AOP (sì, quest'ultima può essere implementata in modo diverso). Come ho già detto, sembra incredibilmente dispendioso essere costretti a riscrivere gran parte dell'infrastruttura già esistente in System.Reflection .


@Wedge:

Hai ragione. Tuttavia, non esiste un caso d'uso specifico qui. Ho modificato la domanda originale per riflettere questo. Il mio interesse è stato suscitato da un'altra domanda in cui il richiedente voleva sapere come poteva iniettare le istruzioni pop e ret alla fine di ogni metodo al fine di impedire a Lutz Roeder's Reflector di reingegnerizzazione del codice sorgente (VB o C #).

Ora, questo scenario può essere realizzato con una serie di strumenti, ad es. PostSharp menzionato sopra e il Reflexil per Reflector, che a sua volta utilizza il libreria Cecil .

Tutto sommato, non sono soddisfatto del framework .NET.

@ Joel:

Sì, sono a conoscenza di questa limitazione. Grazie comunque per averlo sottolineato, poiché è importante.

@marxidad:

Questo sembra l'unico approccio possibile. Tuttavia, ciò significherebbe che dovresti ancora ricreare l'assembly completo usando le classi del builder, giusto? Cioè dovresti camminare su tutto il gruppo manualmente.

Hmm, ci penserò.

È stato utile?

Soluzione

Puoi utilizzare MethodInfo.GetMethodBody (). GetILAsByteArray () , modificarlo e ricollegarlo a MethodBuilder.CreateMethodBody () .

Altri suggerimenti

Mono.Cecil consente inoltre di rimuovere il nome sicuro da un determinato assembly e di salvarlo come assembly senza segno. Dopo aver rimosso il nome sicuro dall'assembly, è possibile modificare l'IL del metodo di destinazione e utilizzare l'assembly come qualsiasi altro assembly. Ecco il link per rimuovere il nome sicuro con Cecil:

http: //groups.google.com/group/mono-cecil/browse_thread/thread/3cc4ac0038c99380/b8ee62b03b56715d?lnk=gst&q=strong+named#b8ee62b03b56715d

Dopo aver rimosso il nome sicuro, puoi praticamente fare quello che vuoi con l'assemblaggio. Buon divertimento!

Sarebbe utile se tu potessi fornire un caso d'uso più specifico, probabilmente ci sono modi migliori per risolvere il tuo problema.

In .NET 3.5 è possibile aggiungere metodi di estensione a classi di framework esistenti, forse è sufficiente?

Un punto importante: se l'assembly è firmato , tutte le modifiche falliranno e finirai con un disastro.

Gli assembly di .NET Framework sono firmati e proprio come ha detto Joel Coehoorn, otterrai un disastro.

Puoi caricare l'assembly usando IronRuby e mescolare tutte le funzionalità che puoi sognare

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top