Closed hackingump closed 1 year ago
The above change leaves memleak for mb_data_status
, so I think the above change needs fixing.
Instead, how about just adding null-check in mailimap_mailbox_data_status_free
?
--- libetpan-1.9.4.orig/src/low-level/imap/mailimap_types.c 2019-11-02 02:58:50.000000000 +0900
+++ libetpan-1.9.4/src/low-level/imap/mailimap_types.c 2022-11-23 14:58:47.075176654 +0900
@@ -1389,9 +1389,12 @@ void
mailimap_mailbox_data_status_free(struct mailimap_mailbox_data_status * info)
{
mailimap_mailbox_free(info->st_mailbox);
- clist_foreach(info->st_info_list, (clist_func) mailimap_status_info_free,
+ if (info->st_info_list)
+ {
+ clist_foreach(info->st_info_list, (clist_func) mailimap_status_info_free,
NULL);
- clist_free(info->st_info_list);
+ clist_free(info->st_info_list);
+ }
free(info);
}
CVE-2022-4121 has been assigned to this issue. @dinhvh, can you take a look, please? Thanks!
Thank you for bringing up this issue!
IMAP STATUS Command Null Pointer Dereference
A segmentation fault due to a null pointer dereference has been found in the IMAP STATUS command handling component. The error occurs when
mailimap_mailbox_data_status_free
in low-level/imap/mailimap_types.c when it tries to freest_info_list
ofmb_data_status
. The segmentation fault is triggered when an invalidSTATUS
response is received. This can at least lead to a Denial Of Service.I have attached a ZIP file, which contains files needed for reproduction.
How to reproduce
See
reproduction_logs.txt
in ZIP on how to reproduce.Expected output:
Explanation of Vulnerability
The null pointer dereference occurs when the
mailimap_mailbox_data_status
structure inmailimap_mailbox_data_status_free
is trying to be freed and theinfo->st_info_list
contains a NULL pointer/is NULL.When the
STATUS
response above is receivedmailimap_mailbox_data_status_parse
is called.mailimap_mailbox_data_status_parse
will callmailimap_struct_spaced_list_parse
. Due to invalid info fields inSTATUS
response,mailimap_struct_spaced_list_parse
will return aMAILIMAP_ERROR_PARSE (code 5)
. With info fields, I am referring to the information fields that should be included inside the parentheses.mailimap_mailbox_data_status_parse
does not stop execution when aMAILIMAP_ERROR_PARSE
is received. Instead, it will continue and callmailimap_mailbox_data_status_new
passing down thestatus_info_list
again, which is NULL. See https://github.com/dinhvh/libetpan/blob/master/src/low-level/imap/mailimap_parser.c#L6613 for theMAILIMAP_ERROR_PARSE
check.mailimap_mailbox_data_status_new
will then not check whetherst_info_list
is NULL and add tomb_data_status
. Below is the snippet ofmailimap_mailbox_data_status_new
.Later, when
mailimap_mailbox_data_status_free
is called to attempt to free the built-up structures, the function does not check whetherst_info_list
is valid and passes it toclist_foreach
. Below are snippets ofclist_foreach
andclist_begin
to illustrate the issue. If a NULL pointer is passed down, this will lead to a segmentation fault.Simplest Fix
The simplest fix I could come up with in a short time period was to check inside
mailimap_mailbox_data_status_new
whetherst_info_list
is NULL. If yes, return NULL. See below:Happy to discuss further and helping in fixing this vulnerability!
PoC-NullPtrDeref-STATUS.zip