J'apprends le C #, alors j'ai créé un petit programme C # qui dit Hello, World!
, puis je l'ai compilé mono-csc
et exécuté avec mono
:
$ mono-csc Hello.cs
$ mono Hello.exe
Hello, World!
J'ai remarqué que quand je frappe TAB
dans bash
, Hello.exe
a été marqué exécutable. En effet, il ne fonctionne que par un shell chargeant le nom du fichier!
Hello.exe
n'est pas un fichier ELF avec une extension de fichier amusante:
$ readelf -a Hello.exe
readelf: Error: Not an ELF file - it has the wrong magic bytes at the start
$ xxd Hello.exe | head -n1
00000000: 4d5a 9000 0300 0000 0400 0000 ffff 0000 MZ..............
MZ
signifie que c'est un exécutable lié statiquement à Microsoft Windows. Déposez-le sur une fenêtre Windows, et il sera (devrait) s'exécuter.
J'ai wine
installé, mais wine
, étant une couche de compatibilité pour les applications Windows, il faut environ 5 fois plus de temps pour s'exécuter en Hello.exe
tant qu'exécutant mono
directement. Par conséquent, ce n'est pas lui wine
qui l'exécute.
Je suppose qu'un mono
module de noyau installé mono
intercepte le exec
/ les appels système, ou capture les fichiers binaires commençant par 4D 5A
, mais lsmod | grep mono
que les amis retournent une erreur.
Que se passe-t-il ici et comment le noyau sait-il que cet exécutable est spécial?
Juste pour prouver que ce n’est pas ma magie qui fonctionne, j’ai utilisé le Crap Shell (alias sh
) pour l’exécuter et il fonctionne toujours en mode natif.
Voici le programme complet, puisqu'un commentateur était curieux:
using System;
class Hello {
/// <summary>
/// The main entry point for the application
/// </summary>
[STAThread]
public static void Main(string[] args) {
System.Console.Write("Hello, World!\n");
}
}
program codefile
. Dans votre cas, le programme est mono, alors que mes exemples incluent php, python, perl et java. Je soupçonne que si mono autoriser l'extension à un fichier autre que .exe toujours exécuté via le code. Cela ne devrait pas dépendre du tout de Windows, car il s'agit finalement d'exécuter un code compilé. Cependant, si votre fichier source a un code dépendant, tel que des API Windows uniquement, il est évident que vous devez avoir besoin de wine pour exécuter ce fichier exe.
/etc/magic
ou /usr/share/file/magic
(ou un endroit magique similaire) est le fichier qui contient les informations nécessaires pour pouvoir le faire.
$ foo.jar
plutôt que $ java -jar foo.jar
- similaire à ce qui est fait pour le mono.
php hello.php
oupython hello.py
ouperl hello.pl
ou dans le cas d’un langage compilé tel que java,java hello
elles s’exécuteraient également car elles ne sont exécutables, mais un programme lit et exécute un fichier. Cependant, si vous courez à la./hello.exe
place demono hello.exe
la, j'ai trouvé votre question et votre réponse plus raisonnables (ce qui, dans le cas contraire, utilise définitivement binfmt-support.