#ifndef cp_cco_action_action_h #define cp_cco_action_action_h /* Cesar project {{{ * * Copyright (C) 2008 Spidcom * * <<>> * * }}} */ /** * \file cp/cco/action/action.h * \brief actions of CCo responsability * \ingroup cp_cco * * CCo action module implements actions of CCo responsability * manage SNID "collisions" (if SNID conflict, a new SNID value shall be chosen) * manage TEI leases (create, suppress, expire) * manage sta association * manage authentication with relevant keys (NEK, NMK) and security-level * in 1st step/version, each sta generates the default NMK from own NPW * (the NMK is used to belong to a given AVLN where all STAs and the CCo * have the same NMK) and the CCo in a given AVLN generates a NEK key * and sends it to stations which perform authentication steps. * * Initialisation of SNID & management of SNID conflicts (section 4.4.1.4 in HP_AV spec) * Le SNID est prévu comme étant une représentation "raccourcie" du NID d'un AVLN * devant également permettre de faire la distinction entre 2 AVLNs ayant des NMKs * respectives différentes mais qui auraient un NID identique (un NID étant * obtenu par hachage SHA256 de NMK, le hachage de 2 NMKs différentes peut * produire un même NID, même si ce cas de figure est statistiquement improbable). * Dans le cas d'un NID identique pour 2 AVLNs ayant chacun une NMK respective * différente de celle de l'autre AVLN, il faut alors un SNID différent pour chacun * des 2 AVLNs. * Une CCo "1" qui détecterait un SNID identique au sien (arrivée d'un Central Beacon * d'une autre CCo "2", donc d'un autre AVLN, avec SNID identique) doit choisir * un autre SNID. * Le SNID qui était en double doit être marqué comme utilisé et la CCo "1" peut * finalement choisir une autre valeur de SNID parmi les SNIDs non utilisés * sur les 16 SNIDs possibles (le SNID est un entier sur 4 bits). * Le choix initial du SNID lorsqu'une station (un équipement) HP_AV s'initialise * puis passe à l'état "Unassociated CCo" ou "CCo" sera un tirage aléatoire entre * 0 inclus et 15 inclus, ce qui permet de diminuer le risque de doublon de SNID * entre les UCCo et CCo sur le même réseau Power-Line au démarrage (mise en route * du secteur avec des équipements fixes connectés, ou branchement d'un ou plusieurs * nouveaux équipements configurés avec un NPW différent de celui des autres équipements * déjà présents, par exemple) * La valeur initiale du SNID ou une nouvelle valeur du SNID déterminée/choisie * après détection d'un conflit de SNID doit être recopiée dans la structure * mac_config pour être rendue disponible dans les couches du Data-Plane qui * utilisent le SNID. Un mécanisme approprié d'activation temporisée d'une nouvelle * valeur du SNID doit être prévu */ BEGIN_DECLS /** * initialisation of CCo action module. * * \param ctx control plane context * * \return pointer to cco_action context */ cco_action_t * cp_cco_action_init(cp_t *ctx); /** * uninitialisation of CCo action module. * * \param ctx control plane context */ void cp_cco_action_uninit(cp_t *ctx); /** * initialisation (reset) of "SNID in use" flags. * * \param ctx control plane context */ void cp_cco_action_reset_snid_flags(cp_t *ctx); /** * check against SNID conflict. * * \param ctx control plane context * \param snid SNID in incoming beacon or MME message * * \return true if SNID conflict, else false * * if the SNID value in argument is in conflict (equal to our own SNID), * it is flagged as already used in the SNID flags, and we should change * our own SNID */ bool cp_cco_action_check_snid_conflict(cp_t *ctx, snid_t snid); /** * choose a new SNID value. * * \param ctx control plane context * \param p_snid pointer to return new snid value chosen * * \return false if new SNID could not be chosen, else true * * \todo what to do if new SNID could not be chosen? * * should be called by the beacon module when it detects conflict between * own SNID of the station (eventually CCo) and the SNID present in a beacon * received by that station (eventually CCo) * * WARNING The initial SNID value or a new SNID value having being chosen * after detecting a SNID conflict shall be copied in the mac_config structure * to be let available in Data-Plane modules that need/use the SNID. An appropriate * mechanism shall be implemented to perform deffered activitation of (new) SNID */ bool cp_cco_action_choose_new_snid(cp_t *ctx, snid_t *p_snid); /** * get a (first) random SNID value. * * \param ctx control plane context * * \return random SNID value between 0 and 15 * * WARNING The initial SNID value having being chosen shall be copied in the * mac_config structure to be let available in Data-Plane modules that need/use * the SNID */ snid_t cp_cco_action_get_random_snid(cp_t *ctx); /** * create a TEI lease for the STA requesting it (one STA associating with the CCo). * * \param ctx control plane context * \param p_tei pointer to return new TEI lease * * \return false if TEI lease creation failed, else true * * TEIs are from 0 to 255 (8 bits integer), the TEI is 0 by default * (TEI=0 indicates that the given STA is not associated) * a TEI is assigned by the CCo to each associating STA, * CCo simply increments a global "TEI index" (1 to 255) * each time a STA is associating and gives the current TEI index value * to the current STA associating. When relooping to 0 , TEI index is forced to 1, * (as TEI=0 is only in not-associated STA context) * CCo itself takes a TEI value (not 0) for its own STA entity */ bool cp_cco_action_create_tei_lease(cp_t *ctx, tei_t *p_tei); /** * renew a TEI lease when required by a STA * (one STA requesting the CCo to renew the TEI lease * it obtained implicitly earlier from that CCo). * * \param ctx control plane context * \param p_tei pointer to TEI lease to be renewed * * \return false if TEI lease renew failed, else true */ bool cp_cco_action_renew_tei_lease(cp_t *ctx, tei_t *p_tei); /** * check for TEI lease expiration. * * \param ctx control plane context * \param p_tei pointer to TEI lease to be checked * * \return true if TEI lease expired, else false * * called by the cco action garbage-collector function for each TEI lease * in the list of TEI lease * * for the given TEI lease, check whether current clock < (TEI creation time + TEI lease time) */ bool cp_cco_action_check_tei_lease(cp_t *ctx, tei_t *p_tei); /** * remove a TEI lease. * * \param ctx control plane context * \param p_tei pointer to TEI lease to be removed * * \return false if removing TEI lease failed, else true */ bool cp_cco_action_remove_tei_lease(cp_t *ctx, tei_t *p_tei); /** * check and release elapsed TEI leases. * * \param ctx control plane context * * For each TEI lease in the TEI map (that is, for each STA in the CCo's AVLN), * * 1) Check if TEI lease-time elapsed (i.e. TEI lease which has its * lease date between the previous garbage date and current garbage date), * this is done by calling cp_cco_action_check_tei_lease() * * 2) If lease-time elapsed, release the given TEI lease, that is, suppress * the STA with that TEI from the AVLN (see 7.3.7 in HP_AV spec) by sending * a CC_LEAVE.IND mme to that STA and suppress the STA element in the CCo dataset, * this is done by calling cp_cco_action_remove_tei_lease() * * 3) if no stations anymore in our AVLN, put a ALL_STA_LEAVED event in the FSM * as to quit the CCo role * * INFO (paragraph 7.3.7 of HP_AV spec) * * "The only secure way to remove a STA from an AVLN is to change the NMK * (refer to Section 7.10.3.7. The DAK of the removed STA should be discarded. * A CCo may send a CC_LEAVE.IND MME to a STA to remove the STA from the AVLN. * The CCo may also change the NEK and not provide the new NEK to the STA * it wants to remove." * * TODO * * change the NMK ? * discard the DAK of the removed STA ? * change the NEK (providing it to all other STAs, except the STA to remove) ? */ void cp_cco_action_check_and_release_elapsed_tei_leases(cp_t *ctx); /** * perform garbage actions of CCo's responsability. * * \param ctx control plane context * * 1) check and release elapsed TEI leases (current clock < TEI creation time + TEI lease time) * this is done by calling cp_cco_action_check_and_release_elapsed_tei_leases() * 2) check NEK expiration (current clock < NEK creation time + 1 hour) * 3) TODO (other garbage actions of CCo's responsability ?) */ void cp_cco_action_garbage(cp_t *ctx); /** * generate a new NEK value. * * \param ctx control plane context * \param sl security level * * \return generated nek value * * NEK shall be used no more than 1 hour, so must be changed after 1 hour * for that purpose, NEK expiration date is checked at every occurrence of * the global garbage collector timer and if current NEK expiration date reached, * a new NEK value shall be generated by calling this function */ nek_t cp_cco_action_gen_nek(cp_t *ctx, u8 sl); /** * treat various interesting info for a CCo (or, may be, even a STA) from * within a received beacon. * * \param ctx control plane context * \param beacon received beacon * * 1) check for SNID conflict between SNID in beacon and own SNID of CCo * 2) if SNID conflict, CCo must prepare itself to change its own SNID * (CCo must choose and reserve another unused SNID, switch to new SNID done later) * 3) treat other infos from within the beacon (useful infos for the CCo or STA) */ void cp_cco_action_manage_rx_beacon(cp_t *ctx, cp_beacon_t *beacon); /** * manage association of a station. * * \param ctx control plane context * \param assoc_req CM_ASSOC.REQ MME msg having being received * * 1) if CC_ASSOC.REQ ReqType field value is "join", call cp_cco_action_create_tei_lease() * to create a default TEI lease (select a TEI value and set 15 minutes of lease date by default, Table 11-212) * 2) else if CC_ASSOC.REQ ReqType field value is "renew", call cp_cco_action_renew_tei_lease() * to update (renew) the TEI lease * (lease = 15 minutes if STA still not authenticated, 48 Hours if STA is authenticated ? Table 11-212) * 3) update CCo dataset (list of TEI lease, and may be TEI / MAC address list ?) * 4) prepare CM_ASSOC.CNF MME to be sent back to the STA that sent the assoc request * 5) send CM_ASSOC.CNF MME back to the STA that sent the assoc request * 6) if the CM_ASSOC.CNF was a positive confirmation, put a STA_JOINED event in the FSM */ void cp_cco_action_manage_sta_assoc(cp_t *ctx, cp_mme_rx_t assoc_req); /** * manage authentication of a station. * * \param ctx control plane context * \param get_key_req CM_GET_KEY.REQ MME msg having being decrypted * * 1) prepare CM_SET_KEY.REQ MME to be sent back to the STA that sent the auth (get key) request * 2) encrypt and encapsulate the CM_SET_KEY.REQ MME into a CM_ENCRYPTED_PAYLOAD.IND MME * 3) send CM_ENCRYPTED_PAYLOAD.IND(CM_SET_KEY.REQ) back to the STA that sent the auth (get key) request */ void cp_cco_action_manage_sta_auth(cp_t *ctx, cp_mme_rx_t get_key_req); END_DECLS #endif /* cp_cco_action_action_h */