J’essaie d’appeler la fonction de reboot
de libc en Python via ctypes
et je ne peux pas le faire fonctionner. J’ai référencé la page de man 2 reboot
( http://linux.die.net/man/2/reboot ). Ma version du kernel est 2.6.35.
Vous trouverez ci-dessous le journal de la console à partir de l’invite Python interactive où j’essaie de faire redémarrer ma machine. Que fais-je mal?
Pourquoi ctypes.get_errno()
ne ctypes.get_errno()
t-il pas?
>>> from ctypes import CDLL, get_errno >>> libc = CDLL('libc.so.6') >>> libc.reboot(0xfee1dead, 537993216, 0x1234567, 0) -1 >>> get_errno() 0 >>> libc.reboot(0xfee1dead, 537993216, 0x1234567) -1 >>> get_errno() 0 >>> from ctypes import c_uint32 >>> libc.reboot(c_uint32(0xfee1dead), c_uint32(672274793), c_uint32(0x1234567), c_uint32(0)) -1 >>> get_errno() 0 >>> libc.reboot(c_uint32(0xfee1dead), c_uint32(672274793), c_uint32(0x1234567)) -1 >>> get_errno() 0 >>>
Modifier:
Via le rappel de Nemos, je peux obtenir get_errno
pour renvoyer 22 (argument invalide). Pas une surprise. Comment devrais-je appeler reboot()
? Je ne transmets clairement pas les arguments attendus par la fonction. =)
Essayer:
>>> libc = CDLL('libc.so.6', use_errno=True)
Cela devrait permettre à get_errno()
de fonctionner.
[mettre à jour]
En outre, le dernier argument est un void *
. S’il s’agit d’un système 64 bits, l’entier 0 n’est pas une représentation valide pour NULL. Je voudrais essayer None
ou peut-être c_void_p(None)
. (Pas sûr comment cela pourrait avoir de l’importance dans ce contexte, cependant.)
[mise à jour 2]
Apparemment, le reboot(0x1234567)
fait l’affaire (voir les commentaires).
Le reboot()
dans libc
est un wrapper autour de l’appel syscall, qui ne prend que l’argument cmd
. Alors essayez:
libc.reboot(0x1234567)
Notez que vous devriez normalement lancer un redémarrage en envoyant SIGINT
au PID 1 – dire au kernel de redémarrer ne permettra pas aux démons du système de s’arrêter proprement et ne synchronisera même pas le cache du système de fichiers sur le disque.