Je souhaite écrire un programme utilisant la nouvelle politique de planification SCHED_DEADLINE
disponible depuis Linux 3.14 .
Je commence avec un programme simple essayant d’utiliser la fonction sched_setattr
.
#include int main(void) { // struct sched_attr attr; // attr.size = sizeof(struct sched_attr); // attr.sched_policy = SCHED_DEADLINE; sched_setattr(0, (void*)0, 0); return 0; }
Cependant, lors de la compilation, j’obtiens l’erreur suivante:
$gcc dead.c dead.c: In function 'main': dead.c:8:2: warning: implicit declaration of function 'sched_setattr' [-Wimplicit-function-declaration] sched_setattr(0, (void*)0, 0); ^~~~~~~~~~~~~ /tmp/ccGxWxZE.o: In function `main': dead.c:(.text+0x19): undefined reference to `sched_setattr' collect2: error: ld returned 1 exit status
Mon système exécute Ubuntu 16.10 Yakkety, avec le kernel 4.8.0-59-generic. Le fichier sched.h
inclus se trouve dans /usr/include/sched.h
et est fourni par le paquet libc6-dev
. Cet en-tête ne contient pas la fonction sched_setattr
et les amis que j’essaie d’utiliser.
Cependant, le kernel (et les en-têtes de kernel) que j’ai installé est fourni avec un fichier d’en-tête sched.h
contenant les définitions dont j’ai besoin. Il se trouve dans /usr/src/linux-headers-4.8.0-58/include/linux/sched.h
, sur mon système.
Donc, je pense naïvement que nous construisons simplement contre les nouveaux en-têtes linux au lieu des en-têtes fournis par libc6-dev. Mon programme ne fonctionnera que sur ce kernel ou sur les kernelx plus récents, mais c’est très bien.
Je modifie la première ligne comme #include
: #include
et exécute:
gcc -I/usr/src/linux-headers-$(uname -r)/include -I/usr/src/linux-headers-$(unam -r)/arch/x86/include dead.c
Maintenant, je reçois page après page des erreurs et des avertissements. Cela ne semble pas la voie à suivre.
Quelle est la bonne façon de construire un programme en espace utilisateur avec des en-têtes Linux plus récents que ceux fournis par la libc?
Et par la suite, comment puis-je construire le programme ci-dessus?
sched_setattr()
est un appel système et ne semble pas avoir d’encapsuleur libc un à un. Vous pouvez faire l’emballage vous-même, quelque chose comme ceci:
#define _GNU_SOURCE #include #include #include #include #include #include #include struct sched_attr { uint32_t size; /* Size of this structure */ uint32_t sched_policy; /* Policy (SCHED_*) */ uint64_t sched_flags; /* Flags */ int32_t sched_nice; /* Nice value (SCHED_OTHER, SCHED_BATCH) */ uint32_t sched_priority; /* Static priority (SCHED_FIFO, SCHED_RR) */ /* Remaining fields are for SCHED_DEADLINE */ uint64_t sched_runtime; uint64_t sched_deadline; uint64_t sched_period; }; static int sched_setattr (pid_t pid, const struct sched_attr *attr, unsigned int flags) { return syscall (SYS_sched_setattr, pid, attr, flags); } int main (int argc, char *argv[]) { struct sched_attr attr; int res; memset (&attr, 0, sizeof (struct sched_attr)); attr.size = sizeof (struct sched_attr); res = sched_setattr (getpid (), &attr, 0); if (res < 0) { perror ("sched_setattr"); return 1; } return 0; }
En struct sched_attr
les erreurs signalées lors de la tentative d'inclusion des fichiers d'en-tête du kernel nécessaires pour obtenir la définition de struct sched_attr
et de la lecture des commentaires trouvés par Googling "en-têtes du kernel dans l'espace utilisateur", je ne peux vraiment pas suggérer d'inclure des fichiers d'en-tête du kernel pour cela .