Tcl Source Code

Check-in [edef464b4f]
Login
Bounty program for improvements to Tcl and certain Tcl packages.
Tcl 2019 Conference, Houston/TX, US, Nov 4-8
Send your abstracts to [email protected]
or submit via the online form by Sep 9.

Many hyperlinks are disabled.
Use anonymous login to enable hyperlinks.

Overview
Comment:Now with fewer memory leaks
Downloads: Tarball | ZIP archive | SQL archive
Timelines: family | ancestors | descendants | both | tip-312-new
Files: files | file ages | folders
SHA3-256: edef464b4f4c615cafb842e399c3639fdfdcf62f2af8f6b4cf1866460f8b1b2a
User & Date: dkf 2019-04-04 23:08:05
Context
2019-04-04
23:47
Clean up and refactor a bit check-in: 258100c83e user: dkf tags: tip-312-new
23:08
Now with fewer memory leaks check-in: edef464b4f user: dkf tags: tip-312-new
22:48
Fix unsigned wide linking. check-in: 5d6108345e user: dkf tags: tip-312-new
Changes
Hide Diffs Unified Diffs Show Whitespace Changes Patch

Changes to generic/tclLink.c.

464
465
466
467
468
469
470



471
472


473


474
475
476
477
478
479
480
481







482
483

484
485
486



487
488
489
490
491
492
493
494
495



496
497
498
499
500
501
502
    Tcl_WideUInt *uwidePtr)
{
    Tcl_WideInt *widePtr = (Tcl_WideInt *) uwidePtr;
    ClientData clientData;
    int type;

    if (TclGetNumberFromObj(NULL, objPtr, &clientData, &type) == TCL_OK) {



	if (type == TCL_NUMBER_BIG) {
	    mp_int num;


	    Tcl_WideUInt scratch, value = 0;


	    unsigned long numBytes = sizeof(Tcl_WideUInt);
	    unsigned char *bytes = (unsigned char *) &scratch;

	    Tcl_GetBignumFromObj(NULL, objPtr, &num);
	    if (num.sign) {
		return 1;
	    }
	    if (mp_to_unsigned_bin_n(&num, bytes, &numBytes) != MP_OKAY) {







		return 1;
	    }

	    while (numBytes-- > 0) {
		value = (value << CHAR_BIT) | *bytes++;
	    }



	    *uwidePtr = value;
	    return 0;
	} else {
	    if (Tcl_GetWideIntFromObj(NULL, objPtr, widePtr) == TCL_OK
		    && (*widePtr >= 0)) {
		return 0;
	    }
	}
    }




    return (GetInvalidWideFromObj(objPtr, widePtr) != TCL_OK);
}

static inline int
GetDouble(
    Tcl_Obj *objPtr,






>
>
>
|

>
>
|
>
>

|


<
<
<
|
>
>
>
>
>
>
>


>



>
>
>

<
<
<
|



|
>
>
>







464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484



485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502



503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
    Tcl_WideUInt *uwidePtr)
{
    Tcl_WideInt *widePtr = (Tcl_WideInt *) uwidePtr;
    ClientData clientData;
    int type;

    if (TclGetNumberFromObj(NULL, objPtr, &clientData, &type) == TCL_OK) {
	if (type == TCL_NUMBER_INT) {
	    *widePtr = *((const Tcl_WideInt *) clientData);
	    return (*widePtr < 0);
	} else if (type == TCL_NUMBER_BIG) {
	    mp_int num;
	    Tcl_WideUInt value = 0;
	    union {
		Tcl_WideUInt value;
		unsigned char bytes[sizeof(Tcl_WideUInt)];
	    } scratch;
	    unsigned long numBytes = sizeof(Tcl_WideUInt);
	    unsigned char *bytes = scratch.bytes;

	    Tcl_GetBignumFromObj(NULL, objPtr, &num);



	    if (num.sign || (MP_OKAY != mp_to_unsigned_bin_n(&num, bytes,
		    &numBytes))) {
		/*
		 * If the sign bit is set (a negative value) or if the value
		 * can't possibly fit in the bits of an unsigned wide, there's
		 * no point in doing further conversion.
		 */
		mp_clear(&num);
		return 1;
	    }
#ifdef WORDS_BIGENDIAN
	    while (numBytes-- > 0) {
		value = (value << CHAR_BIT) | *bytes++;
	    }
#else /* !WORDS_BIGENDIAN */
	    value = scratch.value;
#endif /* WORDS_BIGENDIAN */
	    *uwidePtr = value;



	    mp_clear(&num);
	    return 0;
	}
    }

    /*
     * Evil edge case fallback.
     */

    return (GetInvalidWideFromObj(objPtr, widePtr) != TCL_OK);
}

static inline int
GetDouble(
    Tcl_Obj *objPtr,