Overview
Comment: | Added function to encrypt and decrypt using object command |
---|---|
Downloads: | Tarball | ZIP archive | SQL archive |
Timelines: | family | ancestors | descendants | both | crypto |
Files: | files | file ages | folders |
SHA3-256: |
ae795d4c23fab30f7d92c3a15689a7d9 |
User & Date: | bohagan on 2023-12-02 21:51:17 |
Other Links: | branch diff | manifest | tags |
Context
2023-12-03
| ||
02:24 | Added function to encrypt and decrypt using I/O channel check-in: c3fb3a49db user: bohagan tags: crypto | |
2023-12-02
| ||
21:51 | Added function to encrypt and decrypt using object command check-in: ae795d4c23 user: bohagan tags: crypto | |
20:24 | Added function to encrypt and decrypt a file check-in: db4e2fff2d user: bohagan tags: crypto | |
Changes
Modified generic/tlsDigest.c from [1c3c225c54] to [ecefe3e7e3].
︙ | ︙ | |||
34 35 36 37 38 39 40 41 42 43 44 45 46 47 | #define TYPE_CMAC 0x40 #define TYPE_MAC 0x80 #if OPENSSL_VERSION_NUMBER <= 0x30000000L #define EVP_MAC void #endif /* * This structure defines the per-instance state of a digest operation. */ typedef struct DigestState { Tcl_Channel self; /* This socket channel */ Tcl_TimerToken timer; /* Timer for read events */ | > > | 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 | #define TYPE_CMAC 0x40 #define TYPE_MAC 0x80 #if OPENSSL_VERSION_NUMBER <= 0x30000000L #define EVP_MAC void #endif /*******************************************************************/ /* * This structure defines the per-instance state of a digest operation. */ typedef struct DigestState { Tcl_Channel self; /* This socket channel */ Tcl_TimerToken timer; /* Timer for read events */ |
︙ | ︙ | |||
881 882 883 884 885 886 887 | * Side effects: * Adds data to hash or returns message digest * *------------------------------------------------------------------- */ int DigestInstanceObjCmd(ClientData clientData, Tcl_Interp *interp, int objc, Tcl_Obj *const objv[]) { DigestState *statePtr = (DigestState *) clientData; | | | | | | 883 884 885 886 887 888 889 890 891 892 893 894 895 896 897 898 899 900 901 902 903 904 905 906 907 908 909 910 911 912 913 914 915 916 917 918 919 920 921 922 923 924 925 | * Side effects: * Adds data to hash or returns message digest * *------------------------------------------------------------------- */ int DigestInstanceObjCmd(ClientData clientData, Tcl_Interp *interp, int objc, Tcl_Obj *const objv[]) { DigestState *statePtr = (DigestState *) clientData; int fn, data_len = 0; char *data = NULL; static const char *instance_fns [] = { "finalize", "update", NULL }; dprintf("Called"); /* Validate arg count */ if (objc < 2 || objc > 3) { Tcl_WrongNumArgs(interp, 1, objv, "function ?data?"); return TCL_ERROR; } /* Get function */ if (Tcl_GetIndexFromObj(interp, objv[1], instance_fns, "function", 0, &fn) != TCL_OK) { return TCL_ERROR; } /* Do function */ if (fn) { /* Get data or return error if none */ if (objc == 3) { data = Tcl_GetByteArrayFromObj(objv[2], &data_len); } else { Tcl_WrongNumArgs(interp, 1, objv, "update data"); return TCL_ERROR; } /* Update hash function */ if (DigestUpdate(statePtr, data, (size_t) data_len, 1) != TCL_OK) { return TCL_ERROR; } } else { /* Finalize hash function and calculate message digest */ if (DigestFinalize(interp, statePtr, NULL) != TCL_OK) { return TCL_ERROR; |
︙ | ︙ |
Modified generic/tlsEncrypt.c from [748e9b0eb9] to [5a7f47946f].
︙ | ︙ | |||
26 27 28 29 30 31 32 33 34 35 36 37 38 39 | #define TYPE_CMAC 0x040 #define TYPE_MAC 0x080 #define TYPE_ENCRYPT 0x100 #define TYPE_DECRYPT 0x200 #define TYPE_SIGN 0x400 #define TYPE_VERIFY 0x800 /*******************************************************************/ /* *------------------------------------------------------------------- * * EncryptInitialize -- | > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > | 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 | #define TYPE_CMAC 0x040 #define TYPE_MAC 0x080 #define TYPE_ENCRYPT 0x100 #define TYPE_DECRYPT 0x200 #define TYPE_SIGN 0x400 #define TYPE_VERIFY 0x800 /*******************************************************************/ /* * This structure defines the per-instance state of a encrypt operation. */ typedef struct EncryptState { int type; /* Operation type */ Tcl_Interp *interp; /* Current interpreter */ EVP_CIPHER_CTX *ctx; /* Cipher Context */ Tcl_Command token; /* Command token */ } EncryptState; /* *------------------------------------------------------------------- * * EncryptStateNew -- * * This function creates a per-instance state data structure * * Returns: * State structure pointer * * Side effects: * Creates structure * *------------------------------------------------------------------- */ EncryptState *EncryptStateNew(Tcl_Interp *interp, int type) { EncryptState *statePtr = (EncryptState *) ckalloc((unsigned) sizeof(EncryptState)); if (statePtr != NULL) { memset(statePtr, 0, sizeof(EncryptState)); statePtr->type = type; /* Operation type */ statePtr->interp = interp; /* Current interpreter */ statePtr->ctx = NULL; /* Cipher Context */ statePtr->token = NULL; /* Command token */ } return statePtr; } /* *------------------------------------------------------------------- * * EncryptStateFree -- * * This function deletes a state data structure * * Returns: * Nothing * * Side effects: * Removes structure * *------------------------------------------------------------------- */ void EncryptStateFree(EncryptState *statePtr) { if (statePtr == (EncryptState *) NULL) { return; } /* Free context structures */ if (statePtr->ctx != (EVP_CIPHER_CTX *) NULL) { EVP_CIPHER_CTX_free(statePtr->ctx); } ckfree(statePtr); } /*******************************************************************/ /* *------------------------------------------------------------------- * * EncryptInitialize -- |
︙ | ︙ | |||
189 190 191 192 193 194 195 196 197 198 199 200 201 202 | } /*******************************************************************/ /* *------------------------------------------------------------------- * * EncryptDataHandler -- * * Perform encryption function on a block of data and return result. * * Returns: * TCL_OK or TCL_ERROR * | > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > | 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 298 299 300 301 302 303 304 305 306 307 308 309 310 311 312 313 314 315 316 317 318 319 320 321 322 323 324 325 326 327 328 329 330 331 332 333 334 335 336 337 338 339 340 341 342 343 344 345 346 347 348 349 350 351 352 353 354 355 356 357 358 359 360 361 362 363 364 365 366 367 368 369 370 371 372 373 374 375 376 377 378 379 380 381 382 383 384 385 386 387 388 389 390 391 392 393 394 395 396 397 398 399 400 401 402 403 404 405 406 407 408 409 410 411 412 413 414 415 416 417 418 | } /*******************************************************************/ /* *------------------------------------------------------------------- * * EncryptInstanceObjCmd -- * * Handler for encrypt/decrypt command instances. Used to update * and finalize data for encrypt/decrypt function. * * Returns: * TCL_OK or TCL_ERROR * * Side effects: * Adds data to encrypt/decrypt function * *------------------------------------------------------------------- */ int EncryptInstanceObjCmd(ClientData clientData, Tcl_Interp *interp, int objc, Tcl_Obj *const objv[]) { EncryptState *statePtr = (EncryptState *) clientData; int fn, data_len = 0, out_len; char *data = NULL; Tcl_Obj *resultObj; unsigned char *outbuf; static const char *instance_fns [] = { "finalize", "update", NULL }; dprintf("Called"); /* Validate arg count */ if (objc < 2 || objc > 3) { Tcl_WrongNumArgs(interp, 1, objv, "function ?data?"); return TCL_ERROR; } /* Get function */ if (Tcl_GetIndexFromObj(interp, objv[1], instance_fns, "function", 0, &fn) != TCL_OK) { return TCL_ERROR; } /* Allocate storage for result. Size should be data size + block size. */ resultObj = Tcl_NewObj(); outbuf = Tcl_SetByteArrayLength(resultObj, data_len+EVP_MAX_BLOCK_LENGTH); if (resultObj == NULL || outbuf == NULL) { Tcl_AppendResult(interp, "Memory allocation error", (char *) NULL); Tcl_DecrRefCount(resultObj); return TCL_ERROR; } /* Do function */ if (fn) { /* Get data or return error if none */ if (objc == 3) { data = Tcl_GetByteArrayFromObj(objv[2], &data_len); } else { Tcl_WrongNumArgs(interp, 1, objv, "update data"); Tcl_DecrRefCount(resultObj); return TCL_ERROR; } /* Update function */ if (EncryptUpdate(interp, statePtr->type, statePtr->ctx, outbuf, &out_len, data, data_len) == TCL_OK) { outbuf = Tcl_SetByteArrayLength(resultObj, out_len); Tcl_SetObjResult(interp, resultObj); } else { Tcl_DecrRefCount(resultObj); return TCL_ERROR; } } else { /* Finalize function */ if (EncryptFinalize(interp, statePtr->type, statePtr->ctx, outbuf, &out_len) == TCL_OK) { outbuf = Tcl_SetByteArrayLength(resultObj, out_len); Tcl_SetObjResult(interp, resultObj); } else { Tcl_DecrRefCount(resultObj); return TCL_ERROR; } /* Clean-up */ Tcl_DeleteCommandFromToken(interp, statePtr->token); } return TCL_OK; } /* *------------------------------------------------------------------- * * EncryptCommandDeleteHandler -- * * Callback to clean-up when encrypt/decrypt command is deleted. * * Returns: * Nothing * * Side effects: * Destroys state info structure * *------------------------------------------------------------------- */ void EncryptCommandDeleteHandler(ClientData clientData) { EncryptState *statePtr = (EncryptState *) clientData; /* Clean-up */ EncryptStateFree(statePtr); } /* *------------------------------------------------------------------- * * EncryptCommandHandler -- * * Create command to add data to encrypt/decrypt function. * * Returns: * TCL_OK or TCL_ERROR * * Side effects: * Creates command or error message * *------------------------------------------------------------------- */ int EncryptCommandHandler(Tcl_Interp *interp, int type, Tcl_Obj *cmdObj, Tcl_Obj *cipherObj, Tcl_Obj *digestObj, Tcl_Obj *keyObj, Tcl_Obj *ivObj) { EncryptState *statePtr; char *cmdName = Tcl_GetStringFromObj(cmdObj, NULL); dprintf("Called"); if ((statePtr = EncryptStateNew(interp, type)) == NULL) { Tcl_AppendResult(interp, "Memory allocation error", (char *) NULL); return TCL_ERROR; } /* Initialize function */ if (EncryptInitialize(interp, type, &statePtr->ctx, cipherObj, keyObj, ivObj) != TCL_OK) { EncryptStateFree(statePtr); return TCL_ERROR; } /* Create instance command */ statePtr->token = Tcl_CreateObjCommand(interp, cmdName, EncryptInstanceObjCmd, (ClientData) statePtr, EncryptCommandDeleteHandler); /* Return command name */ Tcl_SetObjResult(interp, cmdObj); return TCL_OK; } /*******************************************************************/ /* *------------------------------------------------------------------- * * EncryptDataHandler -- * * Perform encryption function on a block of data and return result. * * Returns: * TCL_OK or TCL_ERROR * |
︙ | ︙ | |||
218 219 220 221 222 223 224 | if (dataObj != NULL) { data = Tcl_GetByteArrayFromObj(dataObj, &data_len); } else { Tcl_AppendResult(interp, "No data", NULL); return TCL_ERROR; } | | | | 434 435 436 437 438 439 440 441 442 443 444 445 446 447 448 449 450 | if (dataObj != NULL) { data = Tcl_GetByteArrayFromObj(dataObj, &data_len); } else { Tcl_AppendResult(interp, "No data", NULL); return TCL_ERROR; } /* Allocate storage for result. Size should be data size + block size. */ resultObj = Tcl_NewObj(); outbuf = Tcl_SetByteArrayLength(resultObj, data_len+EVP_MAX_BLOCK_LENGTH); if (resultObj == NULL || outbuf == NULL) { Tcl_AppendResult(interp, "Memory allocation error", (char *) NULL); return TCL_ERROR; } /* Perform operation */ if (EncryptInitialize(interp, type, &ctx, cipherObj, keyObj, ivObj) != TCL_OK || |
︙ | ︙ | |||
276 277 278 279 280 281 282 | */ int EncryptFileHandler(Tcl_Interp *interp, int type, Tcl_Obj *inFileObj, Tcl_Obj *outFileObj, Tcl_Obj *cipherObj, Tcl_Obj *digestObj, Tcl_Obj *keyObj, Tcl_Obj *ivObj) { EVP_CIPHER_CTX *ctx = NULL; int total = 0, res, out_len = 0, len; Tcl_Channel in = NULL, out = NULL; unsigned char in_buf[BUFFER_SIZE]; | | | 492 493 494 495 496 497 498 499 500 501 502 503 504 505 506 | */ int EncryptFileHandler(Tcl_Interp *interp, int type, Tcl_Obj *inFileObj, Tcl_Obj *outFileObj, Tcl_Obj *cipherObj, Tcl_Obj *digestObj, Tcl_Obj *keyObj, Tcl_Obj *ivObj) { EVP_CIPHER_CTX *ctx = NULL; int total = 0, res, out_len = 0, len; Tcl_Channel in = NULL, out = NULL; unsigned char in_buf[BUFFER_SIZE]; unsigned char out_buf[BUFFER_SIZE+EVP_MAX_BLOCK_LENGTH]; dprintf("Called"); /* Open input file */ if ((in = Tcl_FSOpenFileChannel(interp, inFileObj, "rb", 0444)) == (Tcl_Channel) NULL) { return TCL_ERROR; } |
︙ | ︙ | |||
384 385 386 387 388 389 390 | dprintf("Called"); /* Clear interp result */ Tcl_ResetResult(interp); /* Validate arg count */ if (objc < 3 || objc > 12) { | | > | > > | | 600 601 602 603 604 605 606 607 608 609 610 611 612 613 614 615 616 617 618 619 620 621 622 623 624 625 626 627 628 629 630 631 632 633 634 635 636 637 638 639 640 641 642 643 644 645 646 647 648 649 650 651 652 653 654 655 | dprintf("Called"); /* Clear interp result */ Tcl_ResetResult(interp); /* Validate arg count */ if (objc < 3 || objc > 12) { Tcl_WrongNumArgs(interp, 1, objv, "-cipher name ?-digest name? -key key ?-iv string? [-command cmdName | -infile filename -outfile filename | -data data]"); return TCL_ERROR; } /* Get options */ for (int idx = 1; idx < objc; idx++) { opt = Tcl_GetStringFromObj(objv[idx], NULL); if (opt[0] != '-') { break; } OPTOBJ("-cipher", cipherObj); OPTOBJ("-command", cmdObj); OPTOBJ("-data", dataObj); OPTOBJ("-digest", digestObj); OPTOBJ("-infile", inFileObj); OPTOBJ("-outfile", outFileObj); OPTOBJ("-key", keyObj); OPTOBJ("-iv", ivObj); OPTBAD("option", "-cipher, -command, -data, -digest, -infile, -key, -iv, -outfile"); return TCL_ERROR; } /* Check for required options */ if (cipherObj == NULL) { Tcl_AppendResult(interp, "No cipher", NULL); } else if (keyObj == NULL) { Tcl_AppendResult(interp, "No key", NULL); return TCL_ERROR; } /* Perform encryption function on file, stacked channel, using instance command, or data blob */ if (inFileObj != NULL && outFileObj != NULL) { res = EncryptFileHandler(interp, type, inFileObj, outFileObj, cipherObj, digestObj, keyObj, ivObj); } else if (cmdObj != NULL) { res = EncryptCommandHandler(interp, type, cmdObj, cipherObj, digestObj, keyObj, ivObj); } else if (dataObj != NULL) { res = EncryptDataHandler(interp, type, dataObj, cipherObj, digestObj, keyObj, ivObj); } else { Tcl_AppendResult(interp, "No operation specified: Use -command, -data, -infile, or -outfile option", NULL); res = TCL_ERROR; } return res; } /* *------------------------------------------------------------------- |
︙ | ︙ |