diff options
author | Anders Broman <anders.broman@ericsson.com> | 2011-07-04 14:07:20 +0000 |
---|---|---|
committer | Anders Broman <anders.broman@ericsson.com> | 2011-07-04 14:07:20 +0000 |
commit | 639e59a9f90f1f0dc4f673f8b1f37c9d64b84834 (patch) | |
tree | b72a5b7d6be3d8e4e5edc594582ce11cd2bcd512 | |
parent | 509c6a7fc070c271ce520739464e22e18e320bb1 (diff) |
From Michael Mann:
Removed "key prefix" need within GUI so it's a little more intuitive (because
that's what this bug is complaining about). Slight backwards compatibility
issue with UAT (because key prefix was in previous keys), but all development
(including fix for BUG 1123 that created UAT) has just been on SVN and not
released.
Also adjusted AirPCap (airpcap_loader.c) to account for the lack of "key
prefix".
Addressed some memory leaks/excess string creation.
https://bugs.wireshark.org/bugzilla/show_bug.cgi?id=5985
svn path=/trunk/; revision=37888
-rw-r--r-- | airpcap_loader.c | 36 | ||||
-rw-r--r-- | epan/crypt/airpdcap.c | 182 | ||||
-rw-r--r-- | epan/crypt/airpdcap_user.h | 15 | ||||
-rw-r--r-- | epan/dissectors/packet-ieee80211.c | 46 |
4 files changed, 122 insertions, 157 deletions
diff --git a/airpcap_loader.c b/airpcap_loader.c index a6ef77364d..1887dd80e6 100644 --- a/airpcap_loader.c +++ b/airpcap_loader.c @@ -149,7 +149,8 @@ static guint num_legacy_channels = 14; static guint get_wep_key(pref_t *pref, gpointer ud) { - gchar *my_string = NULL; + gchar *key_string = NULL; + guint8 key_type = AIRPDCAP_KEY_TYPE_WEP; keys_cb_data_t* user_data; decryption_key_t* new_key; @@ -159,18 +160,33 @@ get_wep_key(pref_t *pref, gpointer ud) if (g_ascii_strncasecmp(pref->name, "wep_key", 7) == 0 && pref->type == PREF_STRING) { - my_string = g_strdup(*pref->varp.string); + /* strip out key type */ + if (g_ascii_strncasecmp(*pref->varp.string, STRING_KEY_TYPE_WEP ":", 4) == 0) { + key_string = (gchar*)(*pref->varp.string)+4; + } + else if (g_ascii_strncasecmp(*pref->varp.string, STRING_KEY_TYPE_WPA_PWD ":", 8) == 0) { + key_string = (gchar*)(*pref->varp.string)+8; + key_type = AIRPDCAP_KEY_TYPE_WPA_PWD; + } + else if (g_ascii_strncasecmp(*pref->varp.string, STRING_KEY_TYPE_WPA_PSK ":", 8) == 0) { + key_string = (gchar*)(*pref->varp.string)+8; + key_type = AIRPDCAP_KEY_TYPE_WPA_PSK; + } + else { + key_type = AIRPDCAP_KEY_TYPE_WEP; + key_string = (gchar*)*pref->varp.string; + } /* Here we have the string describing the key... */ - new_key = parse_key_string(my_string); + new_key = parse_key_string(key_string, key_type); - if( new_key != NULL) - { - /* Key is added only if not null ... */ - user_data->list = g_list_append(user_data->list,new_key); - user_data->number_of_keys++; - user_data->current_index++; - } + if( new_key != NULL) + { + /* Key is added only if not null ... */ + user_data->list = g_list_append(user_data->list,new_key); + user_data->number_of_keys++; + user_data->current_index++; + } } return 0; } diff --git a/epan/crypt/airpdcap.c b/epan/crypt/airpdcap.c index e520882cc3..c96a2a2a29 100644 --- a/epan/crypt/airpdcap.c +++ b/epan/crypt/airpdcap.c @@ -1779,12 +1779,11 @@ AirPDcapRsnaPwd2Psk( /* * Returns the decryption_key_t struct given a string describing the key. - * Returns NULL if the key_string cannot be parsed. + * Returns NULL if the input_string cannot be parsed. */ decryption_key_t* -parse_key_string(gchar* input_string) +parse_key_string(gchar* input_string, guint8 key_type) { - gchar *type; gchar *key; gchar *ssid; @@ -1795,126 +1794,84 @@ parse_key_string(gchar* input_string) gchar **tokens; guint n = 0; decryption_key_t *dk; - gchar *first_nibble = input_string; if(input_string == NULL) return NULL; /* - * Parse the input_string. It should be in the form - * <key type>:<key data>[:<ssid>] - * XXX - For backward compatibility, the a WEP key can be just a string - * of hexadecimal characters (if WEP key is wrong, null will be + * Parse the input_string. WEP and WPA will be just a string + * of hexadecimal characters (if key is wrong, null will be * returned...). + * WPA-PWD should be in the form + * <key data>[:<ssid>] */ - /* First, check for a WEP string */ - /* XXX - This duplicates code in packet-ieee80211.c */ - if (g_ascii_strncasecmp(input_string, STRING_KEY_TYPE_WEP ":", 4) == 0) { - first_nibble += 4; - } - - key_ba = g_byte_array_new(); - res = hex_str_to_bytes(first_nibble, key_ba, FALSE); - - if (res && key_ba->len > 0) { - /* Key is correct! It was probably an 'old style' WEP key */ - /* Create the decryption_key_t structure, fill it and return it*/ - dk = (decryption_key_t *)g_malloc(sizeof(decryption_key_t)); - - dk->type = AIRPDCAP_KEY_TYPE_WEP; - /* XXX - The current key handling code in the GUI requires - * no separators and lower case */ - dk->key = g_string_new(bytes_to_str(key_ba->data, key_ba->len)); - g_string_down(dk->key); - dk->bits = key_ba->len * 8; - dk->ssid = NULL; - - g_byte_array_free(key_ba, TRUE); - return dk; - } - g_byte_array_free(key_ba, TRUE); - - - tokens = g_strsplit(input_string,":",0); - - /* Tokens is a null termiated array of strings ... */ - while(tokens[n] != NULL) - n++; - - if(n < 2) + switch(key_type) { - /* Free the array of strings */ - g_strfreev(tokens); - return NULL; - } - - type = g_strdup(tokens[0]); + case AIRPDCAP_KEY_TYPE_WEP: + case AIRPDCAP_KEY_TYPE_WEP_40: + case AIRPDCAP_KEY_TYPE_WEP_104: + + key_ba = g_byte_array_new(); + res = hex_str_to_bytes(input_string, key_ba, FALSE); + + if (res && key_ba->len > 0) { + /* Key is correct! It was probably an 'old style' WEP key */ + /* Create the decryption_key_t structure, fill it and return it*/ + dk = (decryption_key_t *)g_malloc(sizeof(decryption_key_t)); + + dk->type = AIRPDCAP_KEY_TYPE_WEP; + /* XXX - The current key handling code in the GUI requires + * no separators and lower case */ + dk->key = g_string_new(bytes_to_str(key_ba->data, key_ba->len)); + g_string_down(dk->key); + dk->bits = key_ba->len * 8; + dk->ssid = NULL; + + g_byte_array_free(key_ba, TRUE); + return dk; + } - /* - * The second token is the key (right now it doesn't matter - * if it is a passphrase[+ssid] or an hexadecimal one) - */ - key = g_strdup(tokens[1]); + /* Key doesn't work */ + g_byte_array_free(key_ba, TRUE); + return NULL; - ssid = NULL; - /* Maybe there is a third token (an ssid, if everything else is ok) */ - if(n >= 3) - { - ssid = g_strdup(tokens[2]); - } + case AIRPDCAP_KEY_TYPE_WPA_PWD: - if (g_ascii_strcasecmp(type,STRING_KEY_TYPE_WPA_PSK) == 0) /* WPA key */ - { - /* Create a new string */ - key_string = g_string_new(key); + tokens = g_strsplit(input_string,":",0); - key_ba = g_byte_array_new(); - res = hex_str_to_bytes(key, key_ba, FALSE); + /* Tokens is a null termiated array of strings ... */ + while(tokens[n] != NULL) + n++; - /* Two tokens means that the user should have entered a WPA-BIN key ... */ - if(!res || ((key_string->len) != WPA_PSK_KEY_CHAR_SIZE)) + if(n < 1) { - g_string_free(key_string, TRUE); - g_byte_array_free(key_ba, TRUE); - - g_free(type); - g_free(key); - /* No ssid has been created ... */ /* Free the array of strings */ g_strfreev(tokens); return NULL; } - /* Key was correct!!! Create the new decryption_key_t ... */ - dk = (decryption_key_t*)g_malloc(sizeof(decryption_key_t)); - - dk->type = AIRPDCAP_KEY_TYPE_WPA_PMK; - dk->key = g_string_new(key); - dk->bits = (guint) dk->key->len * 4; - dk->ssid = NULL; + /* + * The first token is the key + */ + key = g_strdup(tokens[0]); - g_string_free(key_string, TRUE); - g_byte_array_free(key_ba, TRUE); - g_free(key); - g_free(type); + ssid = NULL; + /* Maybe there is a second token (an ssid, if everything else is ok) */ + if(n >= 2) + { + ssid = g_strdup(tokens[1]); + } - /* Free the array of strings */ - g_strfreev(tokens); - return dk; - } - else if(g_ascii_strcasecmp(type,STRING_KEY_TYPE_WPA_PWD) == 0) /* WPA key *//* If the number of tokens is more than three, we accept the string... if the first three tokens are correct... */ - { /* Create a new string */ key_string = g_string_new(key); ssid_ba = NULL; - /* Three (or more) tokens mean that the user entered a WPA-PWD key ... */ + /* Two (or more) tokens mean that the user entered a WPA-PWD key ... */ if( ((key_string->len) > WPA_KEY_MAX_CHAR_SIZE) || ((key_string->len) < WPA_KEY_MIN_CHAR_SIZE)) { g_string_free(key_string, TRUE); - g_free(type); g_free(key); g_free(ssid); @@ -1923,13 +1880,12 @@ parse_key_string(gchar* input_string) return NULL; } - if(ssid != NULL) /* more than three tokens found, means that the user specified the ssid */ + if(ssid != NULL) /* more than two tokens found, means that the user specified the ssid */ { ssid_ba = g_byte_array_new(); if (! uri_str_to_bytes(ssid, ssid_ba)) { g_string_free(key_string, TRUE); g_byte_array_free(ssid_ba, TRUE); - g_free(type); g_free(key); g_free(ssid); /* Free the array of strings */ @@ -1942,7 +1898,6 @@ parse_key_string(gchar* input_string) g_string_free(key_string, TRUE); g_byte_array_free(ssid_ba, TRUE); - g_free(type); g_free(key); g_free(ssid); @@ -1964,7 +1919,6 @@ parse_key_string(gchar* input_string) if (ssid_ba != NULL) g_byte_array_free(ssid_ba, TRUE); - g_free(type); g_free(key); if(ssid != NULL) g_free(ssid); @@ -1972,20 +1926,34 @@ parse_key_string(gchar* input_string) /* Free the array of strings */ g_strfreev(tokens); return dk; - } - /* Something was wrong ... free everything */ + case AIRPDCAP_KEY_TYPE_WPA_PSK: - g_free(type); - g_free(key); - if(ssid != NULL) - g_free(ssid); /* It is not always present */ - if (ssid_ba != NULL) - g_byte_array_free(ssid_ba, TRUE); + key_ba = g_byte_array_new(); + res = hex_str_to_bytes(input_string, key_ba, FALSE); - /* Free the array of strings */ - g_strfreev(tokens); + /* Two tokens means that the user should have entered a WPA-BIN key ... */ + if(!res || ((key_ba->len) != WPA_PSK_KEY_CHAR_SIZE)) + { + g_byte_array_free(key_ba, TRUE); + + /* No ssid has been created ... */ + return NULL; + } + + /* Key was correct!!! Create the new decryption_key_t ... */ + dk = (decryption_key_t*)g_malloc(sizeof(decryption_key_t)); + + dk->type = AIRPDCAP_KEY_TYPE_WPA_PMK; + dk->key = g_string_new(input_string); + dk->bits = (guint) dk->key->len * 4; + dk->ssid = NULL; + + g_byte_array_free(key_ba, TRUE); + return dk; + } + /* Type not supported */ return NULL; } diff --git a/epan/crypt/airpdcap_user.h b/epan/crypt/airpdcap_user.h index 1d5e2663c9..1b4836ea80 100644 --- a/epan/crypt/airpdcap_user.h +++ b/epan/crypt/airpdcap_user.h @@ -204,17 +204,20 @@ typedef struct _AIRPDCAP_KEYS_COLLECTION { * - 01:02:03:04:05 (40/64-bit WEP) * - 0102030405060708090a0b0c0d (104/128-bit WEP) * - 01:02:03:04:05:06:07:08:09:0a:0b:0c:0d (104/128-bit WEP) - * - wep:01020304... (WEP) - * - wep:01:02:03:04... (WEP) - * - wpa-pwd:MyPassword (WPA + plaintext password + "wildcard" SSID) - * - wpa-pwd:MyPassword:MySSID (WPA + plaintext password + specific SSID) - * - wpa-psk:01020304... (WPA + 256-bit raw key) + * - MyPassword (WPA + plaintext password + "wildcard" SSID) + * - MyPassword:MySSID (WPA + plaintext password + specific SSID) + * - 01020304... (WPA + 256-bit raw key) + * @param key_type [IN] Type of key used for string. Possibilities include: + * - AIRPDCAP_KEY_TYPE_WEP (40/64-bit and 104/128-bit WEP) + * - AIRPDCAP_KEY_TYPE_WPA_PWD (WPA + plaintext password + "wildcard" SSID or + * WPA + plaintext password + specific SSID) + * - AIRPDCAP_KEY_TYPE_WPA_PSK (WPA + 256-bit raw key) * @return A pointer to a freshly-g_malloc()ed decryption_key_t struct on * success, or NULL on failure. * @see get_key_string() */ decryption_key_t* -parse_key_string(gchar* key_string); +parse_key_string(gchar* key_string, guint8 key_type); /** * Returns a newly allocated string representing the given decryption_key_t diff --git a/epan/dissectors/packet-ieee80211.c b/epan/dissectors/packet-ieee80211.c index 5b472fb9f6..7d1f533255 100644 --- a/epan/dissectors/packet-ieee80211.c +++ b/epan/dissectors/packet-ieee80211.c @@ -166,22 +166,6 @@ static uat_wep_key_record_t *uat_wep_key_records = NULL; static uat_t * wep_uat = NULL; static guint num_wepkeys_uat = 0; -/* - * Convert a raw WEP key or one prefixed with "wep:" to a byte array. - * Separators are allowed. - */ -/* XXX This is duplicated in epan/airpdcap.c:parse_key_string() */ -static gboolean -wep_str_to_bytes(const char *hex_str, GByteArray *bytes) { - char *first_nibble = (char *) hex_str; - - if (g_ascii_strncasecmp(hex_str, STRING_KEY_TYPE_WEP ":", 4) == 0) { - first_nibble += 4; - } - - return hex_str_to_bytes(first_nibble, bytes, FALSE); -} - static void* uat_wep_key_record_copy_cb(void* n, const void* o, size_t siz _U_) { uat_wep_key_record_t* new_key = (uat_wep_key_record_t *)n; const uat_wep_key_record_t* old_key = (uat_wep_key_record_t *)o; @@ -198,31 +182,29 @@ static void* uat_wep_key_record_copy_cb(void* n, const void* o, size_t siz _U_) static void uat_wep_key_record_update_cb(void* r, const char** err) { uat_wep_key_record_t* rec = (uat_wep_key_record_t *)r; decryption_key_t* dk; - gchar* tmpk; if (rec->string == NULL) { *err = ep_strdup_printf("Key can't be blank"); } else { g_strstrip(rec->string); - tmpk = g_strdup(rec->string); - dk = parse_key_string(tmpk); + dk = parse_key_string(rec->string, rec->key); if(dk != NULL) { switch(dk->type) { case AIRPDCAP_KEY_TYPE_WEP: case AIRPDCAP_KEY_TYPE_WEP_40: case AIRPDCAP_KEY_TYPE_WEP_104: - if (rec->key != 0) { + if (rec->key != AIRPDCAP_KEY_TYPE_WEP) { *err = ep_strdup_printf("Invalid key format"); } break; case AIRPDCAP_KEY_TYPE_WPA_PWD: - if (rec->key != 1) { + if (rec->key != AIRPDCAP_KEY_TYPE_WPA_PWD) { *err = ep_strdup_printf("Invalid key format"); } break; case AIRPDCAP_KEY_TYPE_WPA_PSK: - if (rec->key != 2) { + if (rec->key != AIRPDCAP_KEY_TYPE_WPA_PSK) { *err = ep_strdup_printf("Invalid key format"); } break; @@ -12552,9 +12534,9 @@ proto_register_ieee80211 (void) }; static const value_string wep_type_vals[] = { - { 0, STRING_KEY_TYPE_WEP }, - { 1, STRING_KEY_TYPE_WPA_PWD }, - { 2, STRING_KEY_TYPE_WPA_PSK }, + { AIRPDCAP_KEY_TYPE_WEP, STRING_KEY_TYPE_WEP }, + { AIRPDCAP_KEY_TYPE_WPA_PWD, STRING_KEY_TYPE_WPA_PWD }, + { AIRPDCAP_KEY_TYPE_WPA_PSK, STRING_KEY_TYPE_WPA_PSK }, { 0x00, NULL } }; @@ -15789,8 +15771,8 @@ proto_register_ieee80211 (void) prefs_register_static_text_preference(wlan_module, "info_decryption_key", "Key examples: 01:02:03:04:05 (40/64-bit WEP),\n" "010203040506070809101111213 (104/128-bit WEP),\n" - "wpa-pwd:MyPassword[:MyAP] (WPA + plaintext password [+ SSID]),\n" - "wpa-psk:0102030405...6061626364 (WPA + 256-bit key). " + "MyPassword[:MyAP] (WPA + plaintext password [+ SSID]),\n" + "0102030405...6061626364 (WPA + 256-bit key). " "Invalid keys will be ignored.", "Valid key formats"); @@ -15975,16 +15957,13 @@ void set_airpdcap_keys(void) decryption_key_t* dk = NULL; GByteArray *bytes = NULL; gboolean res; - gchar* tmpk = NULL; keys=(PAIRPDCAP_KEYS_COLLECTION)g_malloc(sizeof(AIRPDCAP_KEYS_COLLECTION)); keys->nKeys = 0; for(i = 0; (uat_wep_key_records != NULL) && (i < num_wepkeys_uat) && (i < MAX_ENCRYPTION_KEYS); i++) { - tmpk = g_strdup(uat_wep_key_records[i].string); - - dk = parse_key_string(tmpk); + dk = parse_key_string(uat_wep_key_records[i].string, uat_wep_key_records[i].key); if(dk != NULL) { @@ -15993,7 +15972,7 @@ void set_airpdcap_keys(void) key.KeyType = AIRPDCAP_KEY_TYPE_WEP; bytes = g_byte_array_new(); - res = wep_str_to_bytes(dk->key->str, bytes); + res = hex_str_to_bytes(dk->key->str, bytes, FALSE); if (dk->key->str && res && bytes->len > 0 && bytes->len <= AIRPDCAP_WEP_KEY_MAXLEN) { @@ -16031,7 +16010,7 @@ void set_airpdcap_keys(void) key.KeyType = AIRPDCAP_KEY_TYPE_WPA_PMK; bytes = g_byte_array_new(); - res = wep_str_to_bytes(dk->key->str, bytes); + res = hex_str_to_bytes(dk->key->str, bytes, FALSE); /* XXX - Pass the correct array of bytes... */ if (bytes-> len <= AIRPDCAP_WPA_PMK_LEN) { @@ -16042,7 +16021,6 @@ void set_airpdcap_keys(void) } } } - g_free(tmpk); } /* Now set the keys */ |