REBOL3 tracker
  0.9.12 beta
Ticket #0002171 User: anonymous

Project:

Previous Next
rss
TypeBug Statussubmitted Date27-Sep-2014 03:11
Versionr3 master CategoryUnspecified Submitted byszeng
PlatformAll Severitycrash Prioritynormal

Summary "port/state" shouldn't be free'd when port is being closed
Description The following code crashes interpreter when it's typed in from the console (i.e. not saving as a script and run from there).

The problem is that:
1. when it first opens the port, an lookup event is emitted and saved in system port
the event struct is like:
typedef struct rebol_event {
    u8 type;        // event id (mouse-move, mouse-button, etc)
    u8 flags;        // special flags
    u8 win;        // window id
    u8 model;        // port, object, gui, callback
    u32 data;        // an x/y position or keycode (raw/decoded)
    union {
        REBREQ *req;    // request (for device events)
        void *ser;        // port or object
    };
} REBEVT;

and the memory "req" refers to comes from port/state (see Use_Port_State in core/c-port.c).

2. when it closes the port the, Free_Port_State is called (see core/p-net.c or p-file.c), which changes port/state to "none". So, from now on, the only reference to "req" comes from the lookup event, which has no way to mark it being used.

3. "recycle" frees memory occupied by "req"

4. the old memory occupied by "req" is reused.

5. "recycle" reaches "req" from the event queue, and tries to mark req->port. As the memory is overwritten, it crashes.
Example code
>> repeat n 2 [try [close open open join tcp://localhost: n]]
>> recycle
>> none? file-type? %abc.234
>> recycle

Assigned ton/a Fixed in- Last Update20-Jan-2015 06:58


Comments
(0004508)
szeng
27-Sep-2014 03:20

As a quick test, commenting out the following line fixes the crash:

diff --git a/src/core/p-net.c b/src/core/p-net.c
index 709ccc7..a64d8b5 100644
--- a/src/core/p-net.c
+++ b/src/core/p-net.c
@@ -272,7 +272,7 @@ enum Transport_Types {
OS_DO_DEVICE(sock, RDC_CLOSE);
SET_CLOSED(sock);
}
- Free_Port_State(port);
+ //Free_Port_State(port);
break;

case A_LENGTHQ:


Date User Field Action Change
20-Jan-2015 06:58 abolka Description Modified -
20-Jan-2015 06:58 abolka Code Modified -
27-Sep-2014 03:20 szeng Comment : 0004508 Added -
27-Sep-2014 03:11 szeng Ticket Added -