IEEE Std 802.1X-2010, Figure 11-7 explains that "Parameter set body
length" is exclusive of the suffix padding.
Fix variable length encoding and decoding when CKN length is not a
multiple of 4 bytes.
Signed-off-by: Michael Braun <michael-dev@fami-braun.de>
Mark the data structures used in construction/parsing frames packed to
prevent compiler from being able to pad them.
Signed-off-by: Jouni Malinen <j@w1.fi>
GCM-AES-256 cipher suite is defined in IEEE Std 802.1AEbn-2011.
If authenticator configured as GCM-AES-256, the distributed SAK will be
256 bits indicated by the GCM-AES-256 ID in the MKA packet.
This patch will make AES Key Unwrap to 32 bytes of SAK when identify the
ID.
Signed-off-by: xiaofeis <xiaofeis@codeaurora.org>
These structures are not modified or freed (i.e., only data from them is
copied), so mark the arguments const to document this a bit more clearly
now that there was a memory leak in one of the callers to this function.
Signed-off-by: Jouni Malinen <j@w1.fi>
Log newly generated SAKs as well as unwrapped SAKs with wpa_hexdump_key()
rather than wpa_hexdump(). By default, the wpa_hexdump_key() function
will not display sensitive key data.
Signed-off-by: Michael Siedzik <msiedzik@extremenetworks.com>
In the unlikely event the local KaY and the elected peer have the same
actor priority as well as the same MAC address, log a warning message
and do not elect a key server. Resolution is for network administrator
to reconfigure MAC address.
Signed-off-by: Michael Siedzik <msiedzik@extremenetworks.com>
When the number of live peers becomes 0 the KaY was setting
kay->authenticated true and telling the CP to connect AUTHENTICATED.
Per IEEE Std 802.1X-2010 Clause 12.2, MKA.authenticated means "the Key
Server has proved mutual authentication but has determined that
Controlled Port communication should proceed without the use of MACsec",
which means port traffic will be passed in the clear.
When the number of live peers becomes 0 the KaY must instead set
kay->authenticated false and tell the CP to connect PENDING. Per Clause
12.3 connect PENDING will "prevent connectivity by clearing the
controlledPortEnabled parameter."
Signed-off-by: Michael Siedzik <msiedzik@extremenetworks.com>
Upon receipt of the "MACsec MKPDU SAK Use parameter set" the KaY verifies
that both the latest key and the old key are valid. If the local system
reboots or is reinitialized, the KaY won't have a copy of its old key.
Therefore if the KaY does not have a copy of its old key it should not
reject MKPDUs that contain old key data in the MACsec SAK Use parameter.
Signed-off-by: Michael Siedzik <msiedzik@extremenetworks.com>
KaY looks up participants using CAK Name (CKN). Per IEEE Std 802.1X-2010
Clause 9.3.1 CAK identification, the CKN is an integral number of
octets, between 1 and 32 (inclusive). This fix will ensure that the KaY
does not inadvertently match CKNs such as 'myCakNamedFoo' and
'myCakNamedFooBar'.
Signed-off-by: Michael Siedzik <msiedzik@extremenetworks.com>
ieee802_1x_kay_decode_mkpdu() calls ieee802_1x_mka_i_in_peerlist()
before body_len has been checked on all segments.
ieee802_1x_kay_decode_mkpdu() and ieee802_1x_mka_i_in_peerlist() might
continue and thus underflow left_len even if it finds left_len to small
(or before checking).
Additionally, ieee802_1x_mka_dump_peer_body() might perform out of bound
reads in this case.
Fix this by checking left_len and aborting if too small early.
Signed-off-by: Michael Braun <michael-dev@fami-braun.de>
secy_init_macsec() can fail (if ->macsec_init fails), and
ieee802_1x_kay_init() should handle this and not let MKA run any
further, because nothing is going to work anyway.
On failure, ieee802_1x_kay_init() must deinit its kay, which will free
kay->ctx, so ieee802_1x_kay_init callers (only ieee802_1x_alloc_kay_sm)
must not do it. Before this patch there is a double-free of the ctx
argument when ieee802_1x_kay_deinit() was called.
Signed-off-by: Sabrina Dubroca <sd@queasysnail.net>
ieee802_1x_kay_move_live_peer() did not check
ieee802_1x_kay_get_potential_peer() result explicitly and a static
analyzer reported a warning about the possible NULL result. This cannot
really happen in practice since the only caller of
ieee802_1x_kay_move_live_peer() verifies that the specific peer entry is
available. Anyway, it is easy to silence the false warning by adding an
explicit check here and cover any other potential case if another caller
is added.
Signed-off-by: Jouni Malinen <jouni@qca.qualcomm.com>
ieee802_1x_kay_deinit_transmit_sc() frees the transmit secure channel
data, but secy_delete_transmit_sc() still needs it. Since this functions
are called sequentially, secy_delete_transmit_sc() can be called from
ieee802_1x_kay_deinit_transmit_sc() before txsc is freed.
Fixes: 128f6a98b3 ("mka: Fix the order of operations in secure channel deletion")
Signed-off-by: Davide Caratti <davide.caratti@gmail.com>
ieee802_1x_kay_deinit_receive_sc() frees the receive secure channel data,
but secy_delete_receive_sc() still needs it. Since these two functions
are always called sequentially, secy_delete_receive_sc() can be called
from ieee802_1x_kay_deinit_receive_sc() before rxsc is freed.
Fixes: 128f6a98b3 ("mka: Fix the order of operations in secure channel deletion")
Signed-off-by: Davide Caratti <davide.caratti@gmail.com>
The correct order of deleting a secure channel is to purge all the
secure associations in the channel before actually deleting the secure
channel.
Signed-off-by: Badrish Adiga H R <badrish.adigahr@gmail.com>
Issue: When 2 peers are running MACsec in PSK mode with CA
established, if the interface goes down and comes up after
time > 10 seconds, CA does not get re-established.
Root cause: This is because retry_count of both the peers
would have reached MAX_RETRY_CNT and stays idle for other to
respond. This is clear deadlock situation where peer A waits
for MKA packets from peer B to wake up and vice-versa.
Fix: If MACsec is running in PSK mode, we should send MKPDUs
forever for every 2 seconds.
Signed-off-by: Badrish Adiga H R <badrish.adigahr@gmail.com>
Issue:
------
The test setup has 2 peers running MACsec in PSK mode, Peer A with
MAC address higher than MAC Address of peer B. Test sequence is
1. Peer B starts with actor_priority 255
2. Peer A starts with priority 16, becomes key server.
3. Peer A stops..
4. Peer A restarts with priority 255, but because of the stale values
participant->is_key_server(=TRUE) and participant->is_elected(=TRUE)
it continues to remain as Key Server.
5. For peer B, key server election happens and since it has lower MAC
address as compared to MAC address of A, it becomes the key server.
Now we have 2 key servers in CA and is not correct.
Root-cause & fix:
-----------------
When number of live peers become 0, the flags such lrx, ltx, orx,
otx, etc. need to be cleared. In MACsec PSK mode, these stale values
create problems while re-establishing CA.
Signed-off-by: Badrish Adiga H R <badrish.adigahr@gmail.com>
API ieee802_1x_mka_decode_dist_sak_body() wrongly puts
participant->to_use_sak to TRUE, if Distributed SAK Parameter Set of
length 0 is received. In MACsec PSK mode, this stale incorrect value can
create problems while re-establishing CA. In MACsec PSK mode, CA goes
down if interface goes down and ideally we should be able to
re-establish the CA once interface comes up.
Signed-off-by: Badrish Adiga H R <badrish.adigahr@gmail.com>
This adds a new wpa_supplicant network profile parameter
mka_priority=0..255 to set the priority of the MKA Actor.
Signed-off-by: Badrish Adiga H R <badrish.adigahr@gmail.com>
This uses libnl3 to communicate with the macsec module available on
Linux. A recent enough version of libnl is needed for the macsec.h file
(which is not yet available in a formal libnl release at the time of
this commit).
Signed-off-by: Sabrina Dubroca <sd@queasysnail.net>
Previously, wpa_supplicant only supported hardcoded port == 1 in the
SCI, but users may want to choose a different port.
Signed-off-by: Sabrina Dubroca <sd@queasysnail.net>
So that the user can turn encryption on (MACsec provides
confidentiality+integrity) or off (MACsec provides integrity only). This
commit adds the configuration parameter while the actual behavior change
to disable encryption in the driver is handled in the following commit.
Signed-off-by: Sabrina Dubroca <sd@queasysnail.net>
The first peer may take a long time to come up. In PSK mode we are
basically in a p2p system, and we cannot know when a peer will join the
key exchange. Wait indefinitely, and let the administrator decide if
they want to abort.
Signed-off-by: Sabrina Dubroca <sd@queasysnail.net>
In commit a25e4efc9e ('mka: Add driver op
to get macsec capabilities') I added some code to check the driver's
capabilities. This commit has two problems:
- wrong enum type set in kay->macsec_confidentiality
- ignores that drivers could report MACSEC_CAP_NOT_IMPLEMENTED, in
which case the MKA would claim that MACsec is supported.
Fix this by interpreting MACSEC_CAP_NOT_IMPLEMENTED in the same way as a
DO_NOT_SECURE policy, and set the correct value in
kay->macsec_confidentiality.
Signed-off-by: Sabrina Dubroca <sd@queasysnail.net>
struct data_key already had a 'user' field for reference counting, but
it was basically unused.
Add an ieee802_1x_kay_use_data_key() function to take a reference on a
key, and use ieee802_1x_kay_deinit_data_key() to release the reference.
Signed-off-by: Sabrina Dubroca <sd@queasysnail.net>
Document some data structures from IEEE Std 802.1X-2010, and add the
(not used yet) struct ieee802_1x_mka_dist_cak_body.
Signed-off-by: Sabrina Dubroca <sd@queasysnail.net>
This is specific to the macsec_qca driver. The core implementation
shouldn't care about this, and only deal with the complete secure
channel, and pass this down to the driver.
Drivers that have such limitations should take care of these in their
->create functions and throw an error.
Since the core MKA no longer saves the channel number, the macsec_qca
driver must be able to recover it. Add a map (which is just an array
since it's quite short) to match SCIs to channel numbers, and lookup
functions that will be called in every place where functions would get
the channel from the core code. Getting an available channel should be
part of channel creation, instead of being a preparation step.
Signed-off-by: Sabrina Dubroca <sd@queasysnail.net>
This also implements the macsec_get_capability for the macsec_qca
driver to maintain the existing behavior.
Signed-off-by: Sabrina Dubroca <sd@queasysnail.net>
Clean up the driver interface by passing pointers to struct receive_sc
down the stack to the {create,delete}_recevie_sc() ops, instead of
passing the individual properties of the SC.
Signed-off-by: Sabrina Dubroca <sd@queasysnail.net>
Clean up the driver interface by passing pointers to struct transmit_sc
down the stack to the {create,delete}_transmit_sc() ops, instead of
passing the individual arguments.
Signed-off-by: Sabrina Dubroca <sd@queasysnail.net>
Clean up the driver interface by passing pointers to struct receive_sa
down the stack to the {create,enable,disable}_receive_sa() ops, instead
of passing the individual properties of the SA.
Signed-off-by: Sabrina Dubroca <sd@queasysnail.net>
Clean up the driver interface by passing pointers to struct transmit_sa
down the stack to the {create,enable,disable}_transmit_sa ops, instead
of passing the individual properties of the SA.
Signed-off-by: Sabrina Dubroca <sd@queasysnail.net>
Clean up the driver interface by passing pointers to structs transmit_sa
and receive_sa down the stack to get_receive_lowest_pn(),
get_transmit_next_pn(), and set_transmit_next_pn() ops, instead of
passing the individual arguments.
Signed-off-by: Sabrina Dubroca <sd@queasysnail.net>
These structs will be passed down to macsec drivers in a coming patch to
make the driver interface cleaner, so they need to be shared between the
core MKA implementation and the drivers.
Signed-off-by: Sabrina Dubroca <sd@queasysnail.net>
Assign cs in ieee802_1x_mka_decode_dist_sak_body and reuse it.
Cleanup of key allocation: ieee802_1x_kay_generate_new_sak() and
ieee802_1x_mka_decode_dist_sak_body() both allocate a struct key_conf,
fill it, and ask ieee802_1x_kay_init_data_key() to allocate and set up a
struct data_key. They also allocate multiple key buffers and copy the
same data around. Stop moving data from buffer to buffer, and just
allocate what we really need.
Signed-off-by: Sabrina Dubroca <sd@queasysnail.net>
Instead of copying from kay to a temporary struct, and then from the
struct to the sm, just copy from kay to cp.
Signed-off-by: Sabrina Dubroca <sd@queasysnail.net>
This avoids unnecessary typecasting while still being able to compare
the value to CS_TABLE_SIZE without compiler warnings.
Signed-off-by: Jouni Malinen <j@w1.fi>
Share mka deletion implementation in ieee802_1x_participant_timer() for
the cak_life and mka_life expiration cases.
Signed-off-by: Sabrina Dubroca <sd@queasysnail.net>
This takes care of priority comparison followed by MAC address
comparison if the priorities are identical.
Signed-off-by: Sabrina Dubroca <sd@queasysnail.net>
This is a known constant value (CS_ID_LEN, i.e., the length of the EUI64
identifier) and does not need to be provided separately in these
function calls.
Signed-off-by: Sabrina Dubroca <sd@queasysnail.net>
to_use_sak is a Boolean variable, so there is no need for an if
statement to figure out whether to return TRUE or FALSE.
Signed-off-by: Sabrina Dubroca <sd@queasysnail.net>
Use for loop to remove unnecessary goto use and similar cleanup to
simplify the loops in ieee802_1x_mka_i_in_peerlist(),
ieee802_1x_mka_decode_live_peer_body(), and
ieee802_1x_kay_decode_mkpdu().
Signed-off-by: Sabrina Dubroca <sd@queasysnail.net>
Each loop iteration resets body_peer in the beginning, so there is no
need to increment this pointer in the end.
Signed-off-by: Sabrina Dubroca <sd@queasysnail.net>
Add ieee802_1x_kay_get_potential_peer() similarly to the previously used
ieee802_1x_kay_get_live_peer() and use these helper functions more
consistently to avoid multiple implementations of peer lookups.
Signed-off-by: Sabrina Dubroca <sd@queasysnail.net>
This splits the u32 bitfields into u8 variables and using bitfields only
for the cases where under 8-bit fields are used.
Signed-off-by: Sabrina Dubroca <sd@queasysnail.net>
body_type, used to index in mka_body_handler, can be any u8 value, but
we have only ARRAY_SIZE(mka_body_handler) elements.
Signed-off-by: Sabrina Dubroca <sd@queasysnail.net>
This uses a more accurate variable type for body_type and makes it
cleaner to compare this to other unsigned values.
Signed-off-by: Jouni Malinen <j@w1.fi>
If the memory allocation in ieee802_1x_kay_init_receive_sc() fails, we
end up in an inconsistent state where the peer is moved to the live
peers list and its sci is setup, but we don't have an rxsc.
Signed-off-by: Sabrina Dubroca <sd@queasysnail.net>
The room we actually use is length. This could also mess up the
receiver, since it will advance by the actual length (as indicated by
the parameter body's length), which could differ from the offset at
which we stored the next item.
Signed-off-by: Sabrina Dubroca <sd@queasysnail.net>
1. The comparison between SCI's of two servers with identical priority
is broken, and would always return TRUE. Just use os_memcmp(), which
provides the ordering we need.
2. If no peer can be key server but this instance can, then become the
key server.
3. The ordering of blocks between peer as key server and ourself as key
server overwrites settings. Simple reordering fixes this.
4. Default to being the key server, so that we advertise our ability in
the MKPDUs we send. That's the only way peers can know we can be key
server. Cleared automatically as soon as we find a better peer.
Signed-off-by: Sabrina Dubroca <sd@queasysnail.net>
This is now annotated as be16, so use it as such in all cases instead of
first storing host byte order value and then swapping that to big endian
in other instances of the same structure. This gets rid of number of
sparse warnings.
Signed-off-by: Jouni Malinen <j@w1.fi>
This converts some of the PAE code to use a design that gets rid
unnecessary warnings from sparse and allows more thorough validation of
byte order operations.
Signed-off-by: Jouni Malinen <jouni@qca.qualcomm.com>
Some cases like ifconfig down/up may require MACsec restart. To make
sure the appropriate protect frames and replay parameters get configured
in cases where the interface was down, set these parameters from KaY
configuration to the driver before creating a new transmit SC. This
allows MACsec functionality to recover automatically on such restart.
Signed-off-by: Jouni Malinen <jouni@qca.qualcomm.com>
macsec_validate variable was set incorrectly to FALSE(0) or TRUE(1)
instead of the enum validate_frames values (Disabled(0), Checked(1),
Strict(2). This ended up policy == SHOULD_SECURE to be mapped to
macsec_validate == Checked instead of Strict. This could have resulted
in unintended SecY forwarding of invalid packets rather than dropping
them.
Signed-off-by: Jouni Malinen <jouni@qca.qualcomm.com>
This makes the MACsec implementation more consistent with rest of
wpa_supplicant. (CID 72677, CID 72695, CID 72701, CID 72709, CID 72711)
Signed-off-by: Jouni Malinen <j@w1.fi>
This adds kek_len argument to aes_wrap() and aes_unwrap() functions and
allows AES to be initialized with 192 and 256 bit KEK in addition to
the previously supported 128 bit KEK.
The test vectors in test-aes.c are extended to cover all the test
vectors from RFC 3394.
Signed-off-by: Jouni Malinen <j@w1.fi>
This makes the implementation less likely to provide useful timing
information to potential attackers from comparisons of information
received from a remote device and private material known only by the
authorized devices.
Signed-off-by: Jouni Malinen <j@w1.fi>