4.3.3 Création de messages. Liste de
fonctions
Le fichier « apx_msg_gen.c » permet de
générer les messages qui sont utilisés pour toutes les
communications en s'appuyant sur le protocole API_IPsec Messages (AIM). Dans la
section 4.1.4 on présente ce protocole en expliquant les structures
basiques pour construire un message (HEADER, dm_FUNC TIONS, dm_PARAM,
dm_RESPONSE), le concept de l'encapsulation des messages ainsi que
quelques types de messages (API_MSG_ACK, API_MSG_FUNC
TION...). Ensuite on définit la table complète de type de
messages, de fonctions et de paramètres que l'API_IPsec connaît.
Puis on présente la liste de fonctions développés pour
construire / encapsuler / envoyer / recevoir les messages. Enfin on montre un
exemple pour créer un message.
HEADER (type)
|
ACTION
|
SIGNAL
|
Types de Messages
|
|
Non
|
Serveur principal d'applications bien initialisé
|
APX_SCK_CLOSE
|
Fermer la connexion avec l'API_IPsec
|
Serveur principal d'applications mal initialisé
|
APX_SCK_RES TART
|
Redémarrer l'API_IPsec
|
Redémarrer l'API_IPsec
|
API_MSG_EXI T
|
Sortir de l'API_IPsec (fermer tous les serveurs)
|
Sortir de l'API_IPsec
|
REM_SCK_OPEN
|
Ouvrir 1 connexion avec une API_IPsec distante
|
Serveur principal de 'remotes' bien initialisé
|
REM_SCK_CLOSE
|
Fermer la connexion avec une API_IPsec distante
|
Serveur principal de 'remotes' mal initialisé
|
APX_MSG_ERR
|
Réponse d'erreur
|
APX_MSG_ACK
|
Réponse de confirmation
|
API_MSG_FUNC TION
|
Fonction que doit réaliser l'API_IPsec
|
REM_MSG_FUNCTION
|
Fonction que doit réaliser une API_IPsec distante
|
|
(voir ci-dessous la liste de fonctions)
|
API_SYN_IPSEC
|
Synchronisation de la SAD/SPD avec la DB_SA / DB_SP
|
API_MOBILI TY
|
Message pour la mobilité
|
API_MSG_PARAM
|
Message pour encapsuler X parametres. Il ne s'envoie pas (il ne
définit pas aucune action).
|
|
Table 2. Types de messages de l'API_IPsec
dm_FUNCTION (table, type)
|
dm_PARAM (tag)
|
Type de Fonctions
|
Tags de parametres SA
|
Tags de parametres SP
|
Tags Remote
|
DB_ADD DB_UPDATE DB_READ DB_DELETE DB_DUMP DB_GE TID DB_COPY
|
DB_SA_ID, DB_SA_SPI,
DB_SA_ADR_SRC, DB_SA_ADR_DS T,
DB_SA_TYPE, DB_SA_MODE,
DB_SA_REQ, DB_SA_SEQ,
DB_SA_STATE, DB_SA_WSIZE,
DB_SA_FLAGS, DB_SA_KEYMAT,
DB_SA_KE_TYPE, DB_SA_KE_LEN, DB_SA_KA_TYPE, DB_SA_KA_LEN,
DB_SA_ALLOC, DB_SA_BYTE, DB_SA_ADDTIME, DB_SA_USE TIME
|
DB_SP_ID,
DB SP SPID
_ _ , DB_SP_RANGE_ADR_SRC,
DB_SP_RANGE_ADR_DS T, DB_SP_UPPER_PRO TO, DB_SP_SEQ,
DB_SP_LIFE TIME, DB_SP_VALID TIME, DB_SP_POLICY_LEN,
DB_SP_POLICY, DB_SP_ALL_PARAM
|
REM_PARAM_SFD REM_PARAM_ADR
|
Tables
|
|
|
DB_SA_IDEXT
|
|
|
TB_IKE
|
|
|
|
|
Table 3. Types de fonctions et de paramètres
des messages de l'API_IPsec
|
Etude d'IPsec Projet d'une API_IPSEC pour
la Mobilite et le Multihoming
|
|
|
Ensuite on utilise les abréviations suivantes
:
H = HEADER F = dm_FUNCTION R = dm_RESPONSE P =
dm_PARAM
Fonctions pour crder messages
Ces fonctions créent le HEADER du message et
ajoutent une structure spécifique « dm_XX » avec les
paramètres obligatoires. Elles retournent le pointer *msg qui contient
l'adresse de mémoire du message. msg = create_m sg_respon se
(u_char type, u_char code);
Structure du message : H (type) + R (code) type =
API_MSG_ACK ou API_MSG_ERR
code = value (u_char), Le message de reponse est complete.
RE TURN_PARAM, La reponse ajoutera un parametre (structures
dm_PARAM).
RE TURN_FUNC TION La reponse ajoutera une fonction (structure
dm_FUNC TION).
C'est utile ajouter un parametre a la reponse quand, par
exemple, apres de réaliser une fonction l'API_IPsec veut retourner une
valeur de résultat. On ajoute une fonction quand l'API_IPsec doit
retourner beaucoup de résultats, par exemple, la lecture de plusieurs
parametres d'une SA/SP.
msg = create_m sg_function (u_char table, u_char typefun, u_int
id);
Structure du message : H( type=API_MSG_FUNC TION) + F(table,
typefun) + P(tag) + [ value=id ]
table = TB_SA, TB_SP, TB_MH, TB_MIP, TB_IKE
typefun = DB_ADD, DB_GETID, DB_UPDATE, DB_READ, DB_DELE TE,
DB_COPY, DB_DUMP tag_id = DB_SA_ID, DB_SP_ID
Il existe de messages, comme DB_ADD ou DB_GE TID, qui specifient
seulement le g tag_id D mais n'ajoutent pas aucune valeur de g id D car c'est
un resultat qu'on attend a la reponse.
msg = create_m sg_remote (u_char type, int sfd~rem,
char *adr~rem, void *msgrem);
Structure du message : H1(type) + P(tag) + value + [ H2(type) +
... ]
type = REM_SCK_OPEN, REM_SCK_CLOSE, REM_MSG_FUNC TION tag =
REM_PARAM_SFD ou REM_PARAM_ADR
value = g sfd_rem D ou g adr_rem D
On utilise g msg_rem D avec REM_MSG_FUNC TION pour encapsuler un
message independant qu'on veut envoyer a une API_IPsec distante. Dans ce cas,
la structure du message continue avec le H2.
msg = create_m sg_any (u_char type);
Structure du message : H(type)
type = APX_SCK_XX, API_MSG_EXI T, API_SYN_IPSEC, API_MSG_PARAM
Ces messages n'ont pas besoin de parametres.
|
Etude d'IPsec Projet d'une API_IPSEC pour
la Mobilite et le Multihoming
|
|
|
Fonctions pour ajouter données aux
messages
Ces fonctions ajoutent à la fin d'un message
quelconque une structure F, une structure P ou plusieurs P. Ainsi, à
partir d'un message crée avec les fonctions antérieures, on peut
ajouter plus de paramètres ou des nouvelles fonctions API_MSG_FUNCTION
qui seront exécutés l'une après l'autre par
l'API_IPsec.
msg = add_m sg_function (void *msg, u_char table, u_char
typefun, u_int id);
msg = add_m sg_param (void *msg, u_char tag, u_int16_t length,
void *value);
Ce fonction additionne a la part finale du message une structure
P(tag) + value.
Grace a length, on indique toujours la taille de la valeur :
une structure de plusieurs octets, un entier de quatre octets ou un
caractère d'un octet. Si length est zero et la valeur n'est pas nulle,
la fonction calculera de manière automatique la taille si le type de
paramètre (le tag) est connu. Par contre, si la valeur est nulle, on
passe seulement le tag et non sa valeur, laquelle est prevue normalement dans
la reponse du message.
msg = add_msg_xparam (void *msg, void
*xp);
On peut créer un "message de X
paramètres" avec g xp = create_msg_any(API_MSG_PARAM)
D. Puis on ajoute tous les paramètres qu'on veut avec g add_msg_param D.
Alors, grace a g add_msg_xparam D on élimine le H de g xp D et on ajoute
tous ses paramètres a la part finale de la structure du message
choisit.
Fonction pour obtenir données des
messages
value = get_m sg_param (void *msg, u_char typefun, u_char tag
);
xp = get_m sg_param (void *msg, u_char typefun, 0 );
La suivante fonction permet d'obtenir un paramètre
quelconque contenu dans un message, indiquant le type de fonction (typefun) et
le type de paramètre (tag). La fonction analyse toujours le message pour
savoir quel type de header et quelle structure il contient. Si le message n'a
pas une structure F, la fonction cherche directement le tag. Si le tag est nul,
alors elle retourne tous les paramètres dans un message g xp D.
Fonctions pour envoyer/recevoir
messages
Ces fonctions sont la base de la communication pour l'API_IPsec.
ret = send_m sg (int sfd, void *msg, int length);
Un g send_msg D envoie par le socket identifie par le
descripteur sfd le message de taille length. Si length est zero, on prend la
taille qu'indique le header du message. On remarque qu'après la
transmission, le message est efface et pointer *msg n'est plus valide.
ret = wait_m sg (int sfd, void **ppmsg, int length);
Un g wait_msg D bloque le programme jusqu'à recevoir a
travers du socket de descripteur sfd un message de taille length. Si length est
zero, on regoit un header toujours de taille connu, et grace a qu'il contient
la taille totale on lira le message complètement. Ce message est
sauvegardé en mémoire et on retourne son adresse a travers du
pointer ppmsg.
|
Etude d'IPsec Projet d'une API_IPSEC pour
la Mobilite et le Multihoming
|
|
|
Exemple d'implémentation des
messages
La fonction « value = db_read
(sfd, table, id, *idext, tag);
» est développée à partir des fonctions
antérieurs. Elle permet de lire une SA/SP
référenciée soit par « id » soit par la
structure « IDEXT = (spi, @src, @dst) ». Si cette dernière
structure est utilisée, l'API_IPsec doit exécuter la fonction
DB_GETID pour chercher l'identificateur de la SA/SP avant de réaliser le
DB_READ. On remarque que à la fonction DB_READ on ajoute uniquement un
indicateur de paramètre (le tag) parce qu'on
veut l'obtenir dans le message de réponse. Si « sfd » indique
une API_IPsec distante, on encapsule le message. Puis on envoi le message, on
reçoit la réponse et si elle est de type ACK on peut lire la
valeur du tag demandé.
msg=create_msg_any(API_MSG_FUNC TION);
if(id==0 && idext!=NULL) {
msg = create_msg_function (msg, table, DB_GE TID, id);
msg = add_msg_param(msg, DB_SA_IDEXT, sizeof(t_idext), idext);
}
msg = add_msg_function(msg, table, DB_READ, id);
msg = add_msg_param(msg, tag, 0, NULL); // length=0,
value=NULL 4 only tag !
//header_remote
if(sfd>0 && sfd!=sfd_local)
msg = create_msg_remote(REM_MSG_FUNC TION, sfd, NULL, msg);
//sending...
send_msg(sfd_local,msg, 0);
wait_msg(sfd_local, &msg, 0);
//process response...
if(process_rsp(msg) != API_MSG_ACK) return NULL;
value = get_msg_param(msg, tag, 0); // length = 0 4
length automatique !
|