1/* javasasl.c--Java SASL JNI implementation 2 * Tim Martin 3 */ 4/*********************************************************** 5 Copyright 1998 by Carnegie Mellon University 6 7 All Rights Reserved 8 9Permission to use, copy, modify, and distribute this software and its 10documentation for any purpose and without fee is hereby granted, 11provided that the above copyright notice appear in all copies and that 12both that copyright notice and this permission notice appear in 13supporting documentation, and that the name of Carnegie Mellon 14University not be used in advertising or publicity pertaining to 15distribution of the software without specific, written prior 16permission. 17 18CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO 19THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND 20FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE FOR 21ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 22WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 23ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT 24OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 25******************************************************************/ 26 27#include <config.h> 28#include <stdio.h> 29#include <sasl.h> 30#include <saslutil.h> 31#include <saslplug.h> 32#include <netdb.h> 33#include <sys/types.h> 34#include <sys/socket.h> 35#include <netinet/in.h> 36#include <assert.h> 37 38#include "javasasl.h" 39 40#define VL(x) /* printf x */ 41 42static JNIEnv *globalenv; 43static jobject globalobj; 44 45static int setcomplete(JNIEnv *env, jobject obj); 46 47static void throwexception(JNIEnv *env, int error) 48{ 49 jclass newExcCls; 50 51 VL (("Throwing exception!\n")); 52 53 newExcCls = (*env)->FindClass(env, "CyrusSasl/SaslException"); 54 55 if (newExcCls == 0) { 56 return; 57 } 58 59 (*env)->ThrowNew(env, newExcCls, sasl_errstring(error,NULL,NULL)); 60} 61 62/* server init */ 63 64JNIEXPORT jint JNICALL Java_CyrusSasl_ServerFactory_jni_1sasl_1server_1init 65 (JNIEnv *env, 66 jobject obj __attribute__((unused)), 67 jstring jstr) 68{ 69 /* Obtain a C-copy of the Java string */ 70 const char *str = (*env)->GetStringUTFChars(env, jstr, 0); 71 int result; 72 73 result=sasl_server_init(NULL,str); 74 if (result!=SASL_OK) 75 throwexception(env,result); 76 77 /* Now we are done with str */ 78 (*env)->ReleaseStringUTFChars(env, jstr, str); 79 80 return result; 81} 82 83static int 84log(void *context __attribute__((unused)), 85 int priority, 86 const char *message) 87{ 88 const char *label; 89 jstring jlabel, jmessage; 90 jclass cls; 91 jmethodID mid; 92 93 if (! message) 94 return SASL_BADPARAM; 95 96 switch (priority) { 97 case SASL_LOG_ERR: 98 label = "Error"; 99 break; 100 case SASL_LOG_WARN: 101 label = "Warning"; 102 break; 103 case SASL_LOG_NOTE: 104 label = "Note"; 105 break; 106 case SASL_LOG_FAIL: 107 label = "Fail"; 108 break; 109 case SASL_LOG_PASS: 110 label = "Pass"; 111 break; 112 case SASL_LOG_TRACE: 113 label = "Trace"; 114 break; 115 case SASL_LOG_DEBUG: 116 label = "Debug"; 117 break; 118 default: 119 return SASL_BADPARAM; 120 } 121 122 VL(("I have message %s\n",message)); 123 VL(("Trying to call log callback\n")); 124 cls = (*globalenv)->GetObjectClass(globalenv, globalobj); 125 mid = (*globalenv)->GetMethodID(globalenv, cls, "callback_log", 126 "(Ljava/lang/String;Ljava/lang/String;)V"); 127 if (mid == 0) { 128 return SASL_FAIL; 129 } 130 131 /* make label into a java string */ 132 jlabel= (*globalenv)->NewStringUTF(globalenv,label); 133 134 /* make message into a java string */ 135 jmessage= (*globalenv)->NewStringUTF(globalenv,message); 136 137 /* call java */ 138 (*globalenv)->CallVoidMethod(globalenv, globalobj, mid, 139 jlabel, jmessage); 140 141 /* Now we are done with jlabel */ 142 (*globalenv)->ReleaseStringUTFChars(globalenv, jlabel, label); 143 144 /* Now we are done with jmessage */ 145 (*globalenv)->ReleaseStringUTFChars(globalenv, jmessage, message); 146 147 VL(("done with log callback")); 148 149 return SASL_OK; 150} 151 152static sasl_callback_t callbacks[] = { 153 { 154 SASL_CB_LOG, &log, NULL 155 }, { 156 SASL_CB_PASS, NULL, NULL 157 }, { 158 SASL_CB_USER, NULL, NULL /* we'll handle these ourselves */ 159 }, { 160 SASL_CB_AUTHNAME, NULL, NULL /* we'll handle these ourselves */ 161 }, { 162 /* TODO 163 SASL_CB_ECHOPROMPT, &prompt, NULL 164 }, { 165 SASL_CB_NOECHOPROMPT, &prompt, NULL 166 }, { */ 167 SASL_CB_LIST_END, NULL, NULL 168 } 169}; 170 171/* client init */ 172JNIEXPORT jint JNICALL Java_CyrusSasl_ClientFactory_jni_1sasl_1client_1init 173 (JNIEnv *env, 174 jobject obj __attribute__((unused)), 175 jstring jstr) 176{ 177 /* Obtain a C-copy of the Java string */ 178 const char *str = (*env)->GetStringUTFChars(env, jstr, 0); 179 int result; 180 181 VL(("client initing\n")); 182 183 result=sasl_client_init(callbacks); 184 if (result!=SASL_OK) 185 throwexception(env,result); 186 187 /* Now we are done with str */ 188 (*env)->ReleaseStringUTFChars(env, jstr, str); 189 190 return result; 191} 192 193/* server new */ 194 195JNIEXPORT jint JNICALL Java_CyrusSasl_ServerFactory_jni_1sasl_1server_1new 196 (JNIEnv *env, 197 jobject obj __attribute__((unused)), 198 jstring jservice, 199 jstring jlocal, 200 jint jsecflags) 201{ 202 sasl_conn_t *conn; 203 204 const char *service = (*env)->GetStringUTFChars(env, jservice, 0); 205 const char *local_domain = (*env)->GetStringUTFChars(env, jlocal, 0); 206 const char *user_domain = NULL; 207 int result; 208 209 if (local_domain) { 210 VL(("local domain = %s\n",local_domain)); 211 } 212 if (user_domain) { 213 VL(("user domain = %s\n",user_domain)); 214 } 215 216 result=sasl_server_new(service, local_domain, user_domain, 217 NULL, NULL, NULL, jsecflags, &conn); 218 if (result!=SASL_OK) 219 throwexception(env,result); 220 221 /* Now we are done with str */ 222 (*env)->ReleaseStringUTFChars(env, jservice, service); 223 (*env)->ReleaseStringUTFChars(env, jlocal, local_domain); 224 225 return (jint) conn; 226} 227 228 229JNIEXPORT jint JNICALL JNICALL Java_CyrusSasl_ClientFactory_jni_1sasl_1client_1new 230 (JNIEnv *env, 231 jobject obj __attribute__((unused)), 232 jstring jservice, jstring jserver, jint jsecflags, jboolean successdata) 233{ 234 sasl_conn_t *conn; 235 236 const char *service = (*env)->GetStringUTFChars(env, jservice, 0); 237 const char *serverFQDN = (*env)->GetStringUTFChars(env, jserver, 0); 238 int result; 239 240 result=sasl_client_new(service, serverFQDN, NULL, NULL, NULL, 241 jsecflags | (successdata ? SASL_SUCCESS_DATA : 0), 242 &conn); 243 244 if (result!=SASL_OK) 245 throwexception(env,result); 246 247 /* Now we are done with str */ 248 (*env)->ReleaseStringUTFChars(env, jservice, service); 249 (*env)->ReleaseStringUTFChars(env, jserver, serverFQDN); 250 251 return (jint) conn; 252} 253 254/* server start */ 255 256JNIEXPORT jbyteArray JNICALL Java_CyrusSasl_GenericServer_jni_1sasl_1server_1start 257 (JNIEnv *env, 258 jobject obj __attribute__((unused)), 259 jint ptr, jstring jstr, jbyteArray jarr, jint jlen) 260{ 261 sasl_conn_t *conn; 262 const char *mech = (*env)->GetStringUTFChars(env, jstr, 0); 263 const char *out; 264 unsigned int outlen; 265 int result; 266 jbyteArray arr; 267 char *tmp; 268 char *in=NULL; 269 270 VL(("in server start\n")); 271 272 if (jarr!=NULL) 273 in = (*env)->GetByteArrayElements(env, jarr, 0); 274 275 conn=(sasl_conn_t *) ptr; 276 277 result=sasl_server_start(conn, mech, 278 (const char *) in, jlen, 279 &out, &outlen); 280 281 if ((result!=SASL_OK) && (result!=SASL_CONTINUE)) 282 { 283 284 throwexception(env,result); 285 return NULL; 286 } 287 288 /* Because SASLv2 does not allow for persistance, we'll copy 289 * it here */ 290 tmp = malloc(outlen); 291 if(!tmp) { 292 throwexception(env, SASL_NOMEM); 293 return NULL; 294 } 295 296 memcpy(tmp, out, outlen); 297 298 arr=(*env)->NewByteArray(env,outlen); 299 (*env)->SetByteArrayRegion(env,arr, 0, outlen, (char *)tmp); 300 301 return arr; 302} 303 304 305static int getvalue(JNIEnv *env, jobject obj, char *funcname, char **result, int *len) 306{ 307 jclass cls; 308 jmethodID mid; 309 const char *str; 310 jstring jstr; 311 312 /* set up for java callback */ 313 cls = (*env)->GetObjectClass(env, obj); 314 mid = (*env)->GetMethodID(env, cls, funcname, 315 "(I)Ljava/lang/String;"); 316 if (mid == 0) { 317 VL(("Can't find %s callback!!!\n",funcname)); 318 return SASL_FAIL; 319 } 320 321 VL(("do the callback\n")); 322 jstr = (jstring) (*env)->CallObjectMethod(env, obj, mid); 323 324 if (jstr) { 325 VL(("convert the result string into a char *\n")); 326 str = (*env)->GetStringUTFChars(env, jstr, 0); 327 328 /* copy password into the result */ 329 *result=(char *) malloc( strlen(str)); 330 strcpy(*result, str); 331 *len=strlen(str); 332 333 /* Now we are done with str */ 334 (*env)->ReleaseStringUTFChars(env, jstr, str); 335 } else { 336 *result = NULL; 337 *len = 0; 338 } 339 340 return SASL_OK; 341} 342 343static int callall_callbacks(JNIEnv *env, jobject obj, 344 int calluid,int callaid, 345 int callpass,int callrealm) 346{ 347 jclass cls; 348 jmethodID mid; 349 350 /* set up for java callback */ 351 cls = (*env)->GetObjectClass(env, obj); 352 mid = (*env)->GetMethodID(env, cls, "do_callbacks", "(IIII)V"); 353 if (mid == 0) { 354 VL(("Can't find do_callbacks callback!!!\n")); 355 return SASL_FAIL; 356 } 357 358 /* do the callback */ 359 (*env)->CallVoidMethod(env, obj, mid,calluid,callaid,callpass,callrealm); 360 361 VL(("callall_callbacks worked\n")); 362 return SASL_OK; 363} 364 365/* 366 * Fills in all the prompts by doing callbacks to java 367 * returns SASL_INTERACT on sucess 368 */ 369 370static int fillin_interactions(JNIEnv *env, jobject obj, 371 sasl_interact_t *tlist) 372{ 373 sasl_interact_t *ptr=tlist; 374 sasl_interact_t *uid=NULL; int is_uid = 0; 375 sasl_interact_t *aid=NULL; int is_aid = 0; 376 sasl_interact_t *pass=NULL;int is_pass = 0; 377 sasl_interact_t *realm=NULL; int is_realm = 0; 378 379 /* First go through the prompt list to see what we have */ 380 while (ptr->id!=SASL_CB_LIST_END) 381 { 382 if (ptr->id==SASL_CB_PASS) 383 { pass=ptr; is_pass = 1; } 384 if (ptr->id==SASL_CB_AUTHNAME) 385 { aid=ptr; is_aid = 1; } 386 if (ptr->id==SASL_CB_USER) 387 { uid=ptr; is_uid = 1; } 388 if (ptr->id==SASL_CB_GETREALM) 389 { realm = ptr; is_realm = 1; } 390 ptr->result=NULL; 391 392 /* increment to next sasl_interact_t */ 393 ptr++; 394 } 395 396 callall_callbacks(env,obj,is_uid,is_aid,is_pass,is_realm); 397 398 if (is_pass) { 399 VL(("in is_pass\n")); 400 401 getvalue(env,obj,"get_password",(char **) &(pass->result),(int *) &(pass->len)); 402 } 403 if (is_aid) { 404 VL(("in is_aid\n")); 405 406 getvalue(env,obj,"get_authid",(char **) &(aid->result),(int *) &(aid->len)); 407 } 408 if (is_uid) { 409 VL(("in is_uid\n")); 410 411 getvalue(env,obj,"get_userid",(char **) &(uid->result),(int *) &(uid->len)); 412 } 413 if (is_realm) { 414 VL(("in is_realm\n")); 415 416 getvalue(env,obj,"get_realm",(char **) &(realm->result),(int *) &(realm->len)); 417 } 418 419 /* everything should now be filled in (i think) */ 420 VL(("everything should now be filled in (i think)\n")); 421 422 return SASL_INTERACT; 423} 424 425/* client start */ 426 427JNIEXPORT jbyteArray JNICALL Java_CyrusSasl_GenericClient_jni_1sasl_1client_1start(JNIEnv *env, jobject obj, jint ptr, jstring jstr) 428{ 429 sasl_conn_t *conn=(sasl_conn_t *) ptr; 430 const char *mechlist = (*env)->GetStringUTFChars(env, jstr, 0); 431 const char *out; 432 unsigned int outlen=0; 433 const char *mechusing; 434 int result; 435 sasl_interact_t *client_interact=NULL; 436 char *tmp; 437 jbyteArray arr; 438 jstring jmechusing; 439 jclass cls; 440 jmethodID mid; 441 442 VL(("sasl_start")); 443 444 do { 445 446 result=sasl_client_start(conn, mechlist, 447 &client_interact, 448 &out, 449 &outlen, 450 &mechusing); 451 452 if (result==SASL_INTERACT) { 453 int res2 = fillin_interactions(env,obj,client_interact); 454 } 455 456 } while (result==SASL_INTERACT); 457 458 /* ok release mechlist */ 459 (*env)->ReleaseStringUTFChars(env, jstr, mechlist); 460 461 if ((result!=SASL_OK) && (result!=SASL_CONTINUE)) 462 { 463 throwexception(env,result); 464 return NULL; 465 } 466 467 /* tell the java layer what mechanism we're using */ 468 469 /* set up for java callback */ 470 cls = (*env)->GetObjectClass(env, obj); 471 mid = (*env)->GetMethodID(env, cls, "callback_setmechanism", 472 "(Ljava/lang/String;I)V"); 473 if (mid == 0) { 474 throwexception(env,SASL_FAIL); 475 return NULL; 476 } 477 478 VL(("mechusing=%s\n",mechusing)); 479 480 /* make into mech */ 481 jmechusing= (*env)->NewStringUTF(env,mechusing); 482 483 /* do the callback */ 484 (*env)->CallVoidMethod(env, obj, mid,jmechusing); 485 486 /* Because SASLv2 does not allow for persistance, we'll copy 487 * it here */ 488 tmp = malloc(outlen); 489 if(!tmp) { 490 throwexception(env, SASL_NOMEM); 491 return NULL; 492 } 493 494 memcpy(tmp, out, outlen); 495 496 arr=(*env)->NewByteArray(env,outlen); 497 (*env)->SetByteArrayRegion(env,arr, 0, outlen, (char *)tmp); 498 499 return arr; 500} 501 502/* server step */ 503 504JNIEXPORT jbyteArray JNICALL Java_CyrusSasl_GenericServer_jni_1sasl_1server_1step 505 506 (JNIEnv *env, 507 jobject obj __attribute__((unused)), 508 jint ptr, jbyteArray jarr, jint jlen) 509{ 510 sasl_conn_t *conn=(sasl_conn_t *) ptr; 511 int result; 512 const char *out; 513 unsigned int outlen; 514 jbyteArray arr; 515 char *in = NULL; 516 char *tmp; 517 518 if (jlen > 0) 519 in = (*env)->GetByteArrayElements(env, jarr, 0); 520 521 result=sasl_server_step(conn, (const char *) in, jlen, 522 &out, &outlen); 523 524 if ((result!=SASL_OK) && (result!=SASL_CONTINUE)) 525 { 526 VL (("Throwing exception! %d\n",result)); 527 /* throw exception */ 528 throwexception(env,result); 529 return NULL; 530 } 531 532 if (result == SASL_OK) { 533 setcomplete(env,obj); 534 } 535 536 if (jlen > 0) 537 (*env)->ReleaseByteArrayElements(env, jarr,in ,0); 538 539 /* Because SASLv2 does not allow for persistance, we'll copy 540 * it here */ 541 tmp = malloc(outlen); 542 if(!tmp) { 543 throwexception(env, SASL_NOMEM); 544 return NULL; 545 } 546 547 memcpy(tmp, out, outlen); 548 549 arr=(*env)->NewByteArray(env,outlen); 550 (*env)->SetByteArrayRegion(env,arr, 0, outlen, (char *)tmp); 551 552 return arr; 553} 554 555 556/* 557 * Tell client we're done 558 */ 559static int setcomplete(JNIEnv *env, jobject obj) 560{ 561 jclass cls; 562 jmethodID mid; 563 564 VL (("Complete!\n")); 565 566 /* set up for java callback */ 567 cls = (*env)->GetObjectClass(env, obj); 568 mid = (*env)->GetMethodID(env, cls, "setcomplete", 569 "(I)V"); 570 if (mid == 0) { 571 VL(("Can't find do_callbacks callback!!!\n")); 572 return SASL_FAIL; 573 } 574 575 /* do the callback */ 576 (*env)->CallVoidMethod(env, obj, mid, 5); 577 578 return SASL_OK; 579} 580 581/* client step */ 582 583JNIEXPORT jbyteArray JNICALL Java_CyrusSasl_GenericClient_jni_1sasl_1client_1step 584 (JNIEnv *env, jobject obj, jint ptr, jbyteArray jarr, jint jlen) 585{ 586 sasl_conn_t *conn=(sasl_conn_t *) ptr; 587 /* const char *in = (*env)->GetStringUTFChars(env, jstr, 0);*/ 588 int result; 589 sasl_interact_t *client_interact=NULL; 590 const char *out; 591 unsigned int outlen; 592 jbyteArray arr; 593 char *in; 594 char *tmp; 595 596 VL(("in client step\n")); 597 598 if (jarr) { 599 in = (*env)->GetByteArrayElements(env, jarr, 0); 600 in[jlen]=0; 601 } else { 602 assert(jlen == 0); 603 in = NULL; 604 } 605 606 VL(("in client step 2\n")); 607 608 globalenv=env; 609 globalobj=obj; 610 611 do { 612 result=sasl_client_step(conn, (const char *) in, jlen, 613 &client_interact, 614 &out, &outlen); 615 616 VL(("in client step 3\n")); 617 618 if (result==SASL_INTERACT) { 619 result = fillin_interactions(env,obj,client_interact); 620 } 621 } while (result==SASL_INTERACT); 622 623 if ((result!=SASL_OK) && (result!=SASL_CONTINUE)) { 624 /* throw exception */ 625 VL (("Throwing exception %d\n",result)); 626 throwexception(env,result); 627 return NULL; 628 } 629 630 if (result == SASL_OK) { 631 VL (("Setting complete\n")); 632 setcomplete(env,obj); 633 } 634 635 if (jarr) { 636 VL(("about to releasebytearrayelements\n")); 637 (*env)->ReleaseByteArrayElements(env, jarr,in ,0); 638 } 639 640 /* Because SASLv2 does not allow for persistance, we'll copy 641 * it here */ 642 tmp = malloc(outlen); 643 if(!tmp) { 644 throwexception(env, SASL_NOMEM); 645 return NULL; 646 } 647 648 VL(("in client step 4\n")); 649 650 memcpy(tmp, out, outlen); 651 652 arr=(*env)->NewByteArray(env,outlen); 653 (*env)->SetByteArrayRegion(env,arr, 0, outlen, (char *)tmp); 654 655 VL(("returning arr\n")); 656 return arr; 657} 658 659 660JNIEXPORT void JNICALL Java_CyrusSasl_GenericCommon_jni_1sasl_1set_1prop_1string 661 (JNIEnv *env, 662 jobject obj __attribute__((unused)), 663 jint ptr, jint propnum, jstring val) 664{ 665 sasl_conn_t *conn=(sasl_conn_t *) ptr; 666 const char *value = (*env)->GetStringUTFChars(env, val, 0); 667 668 int result=sasl_setprop(conn, propnum, value); 669 670 if (result!=SASL_OK) 671 throwexception(env,result); 672} 673 674 675JNIEXPORT void JNICALL Java_CyrusSasl_GenericCommon_jni_1sasl_1set_1prop_1int 676 (JNIEnv *env, 677 jobject obj __attribute__((unused)), 678 jint ptr, jint propnum, jint jval) 679{ 680 681 sasl_conn_t *conn=(sasl_conn_t *) ptr; 682 int value=jval; 683 int result; 684 685 VL(("sasl conn = %d\n",conn)); 686 VL (("propnum = %d\n",propnum)); 687 688 result=sasl_setprop(conn, propnum, &value); 689 690 VL (("setprop returned %d\n",result)); 691 692 if (result!=SASL_OK) 693 throwexception(env,result); 694} 695JNIEXPORT void JNICALL Java_CyrusSasl_GenericCommon_jni_1sasl_1set_1prop_1bytes 696 (JNIEnv *env, 697 jobject obj __attribute__((unused)), 698 jint ptr, jint propnum, jbyteArray jarr) 699{ 700 char *value = (*env)->GetByteArrayElements(env, jarr, 0); 701 sasl_conn_t *conn=(sasl_conn_t *) ptr; 702 int result; 703 704 result=sasl_setprop(conn, propnum, value); 705 if (result!=SASL_OK) 706 throwexception(env,result); 707 708} 709 710/* encode */ 711JNIEXPORT jbyteArray JNICALL Java_CyrusSasl_GenericCommon_jni_1sasl_1encode 712 (JNIEnv *env, 713 jobject obj __attribute__((unused)), 714 jint ptr, 715 jbyteArray jarr, jint jlen) 716{ 717 sasl_conn_t *conn=(sasl_conn_t *) ptr; 718 char *in = (*env)->GetByteArrayElements(env, jarr, 0); 719 const char *out; 720 unsigned int outlen; 721 char *tmp; 722 int result; 723 jbyteArray arr; 724 725 result=sasl_encode(conn,(const char *) in, jlen, &out, &outlen); 726 if (result!=SASL_OK) 727 throwexception(env,result); 728 729 /* Because SASLv2 does not allow for persistance, we'll copy 730 * it here */ 731 tmp = malloc(outlen); 732 if(!tmp) { 733 throwexception(env, SASL_NOMEM); 734 return NULL; 735 } 736 737 memcpy(tmp, out, outlen); 738 739 arr=(*env)->NewByteArray(env,outlen); 740 (*env)->SetByteArrayRegion(env,arr, 0, outlen, (char *)tmp); 741 742 return arr; 743} 744 745/* decode */ 746JNIEXPORT jbyteArray JNICALL Java_CyrusSasl_GenericCommon_jni_1sasl_1decode 747 (JNIEnv *env, 748 jobject obj __attribute__((unused)), 749 jint ptr, jbyteArray jarr, jint jlen) 750{ 751 752 sasl_conn_t *conn=(sasl_conn_t *) ptr; 753 char *in = (*env)->GetByteArrayElements(env, jarr, 0); 754 const char *out; 755 unsigned int outlen=9; 756 char *tmp; 757 int inlen=jlen; 758 int result; 759 jbyteArray arr; 760 761 result=sasl_decode(conn, (const char *) in, inlen, &out, &outlen); 762 if (result!=SASL_OK) 763 throwexception(env,result); 764 765 766 /* Because SASLv2 does not allow for persistance, we'll copy 767 * it here */ 768 tmp = malloc(outlen); 769 if(!tmp) { 770 throwexception(env, SASL_NOMEM); 771 return NULL; 772 } 773 774 memcpy(tmp, out, outlen); 775 776 arr=(*env)->NewByteArray(env,outlen); 777 (*env)->SetByteArrayRegion(env,arr, 0, outlen, (char *)tmp); 778 779 (*env)->ReleaseByteArrayElements(env, jarr, in,0); 780 781 return arr; 782 783} 784 785/*JNIEXPORT jbyteArray JNICALL Java_sasl_saslServerConn_jni_1sasl_1server_1decode 786 (JNIEnv *env, jobject obj, jint ptr, jbyteArray in, jint inlen) 787{ 788 return Java_sasl_saslClientConn_jni_1sasl_1client_1decode(env,obj,ptr,in,inlen); 789 }*/ 790 791JNIEXPORT void JNICALL Java_CyrusSasl_CommonConn_jni_1sasl_1dispose 792 (JNIEnv *env __attribute__((unused)), 793 jobject obj __attribute__((unused)), 794 jint ptr) 795{ 796 sasl_conn_t *conn=(sasl_conn_t *) ptr; 797 798 sasl_dispose(&conn); 799 800} 801 802JNIEXPORT jstring JNICALL Java_CyrusSasl_ServerFactory_jni_1sasl_1server_1getlist 803 (JNIEnv *env, 804 jobject obj __attribute__((unused)), 805 jint ptr, jstring jpre, jstring jsep, jstring jsuf) 806{ 807 sasl_conn_t *conn=(sasl_conn_t *) ptr; 808 const char *pre = (*env)->GetStringUTFChars(env, jpre, 0); 809 const char *sep = (*env)->GetStringUTFChars(env, jsep, 0); 810 const char *suf = (*env)->GetStringUTFChars(env, jsuf, 0); 811 const char *list; 812 unsigned int plen; 813 jstring ret; 814 815 int result=sasl_listmech(conn, NULL, pre, sep, suf, &list, &plen, NULL); 816 817 if (result!=SASL_OK) 818 { 819 throwexception(env,result); 820 return NULL; 821 } 822 823 ret= (*env)->NewStringUTF(env,list); 824 if (ret==NULL) 825 throwexception(env, -1); 826 827 return ret; 828} 829 830JNIEXPORT void JNICALL Java_CyrusSasl_GenericCommon_jni_1sasl_1set_1server 831 (JNIEnv *env, 832 jobject obj __attribute__((unused)), 833 jint ptr, jbyteArray jarr, jint jport) 834{ 835 sasl_conn_t *conn=(sasl_conn_t *) ptr; 836 unsigned char *ip = (*env)->GetByteArrayElements(env, jarr, 0); 837 char out[52]; 838 int result; 839 840 sprintf(out, "%d.%d.%d.%d;%d", ip[0], ip[1], ip[2], ip[3], (int)jport); 841 842 result=sasl_setprop(conn, SASL_IPREMOTEPORT, out); 843 844 VL(("Set IP_REMOTE: %s: %d\n",out, result)); 845 846 /* if not set throw an exception */ 847 if (result!=SASL_OK) 848 throwexception(env,result); 849} 850 851 852 853JNIEXPORT void JNICALL Java_CyrusSasl_GenericCommon_jni_1sasl_1set_1client 854 (JNIEnv *env, 855 jobject obj __attribute__((unused)), 856 jint ptr, jbyteArray jarr, jint jport) 857{ 858 sasl_conn_t *conn=(sasl_conn_t *) ptr; 859 unsigned char *ip = (*env)->GetByteArrayElements(env, jarr, 0); 860 char out[52]; 861 int result; 862 863 sprintf(out, "%d.%d.%d.%d;%d", ip[0], ip[1], ip[2], ip[3], (int)jport); 864 865 result=sasl_setprop(conn, SASL_IPLOCALPORT, out); 866 867 VL(("Set IP_LOCAL: %s: %d\n",out, result)); 868 869 /* if not set throw and exception */ 870 if (result!=SASL_OK) 871 throwexception(env,result); 872} 873 874/* allocate a secprops structure */ 875 876static sasl_security_properties_t *make_secprops(int min,int max) 877{ 878 sasl_security_properties_t *ret=(sasl_security_properties_t *) 879 malloc(sizeof(sasl_security_properties_t)); 880 881 ret->maxbufsize=1024; 882 ret->min_ssf=min; 883 ret->max_ssf=max; 884 885 ret->security_flags=0; 886 ret->property_names=NULL; 887 ret->property_values=NULL; 888 889 return ret; 890} 891 892 893JNIEXPORT void JNICALL Java_CyrusSasl_GenericCommon_jni_1sasl_1setSecurity 894 (JNIEnv *env, 895 jobject obj __attribute__((unused)), 896 jint ptr, jint minssf, jint maxssf) 897{ 898 int result=SASL_FAIL; 899 sasl_conn_t *conn=(sasl_conn_t *) ptr; 900 sasl_security_properties_t *secprops=NULL; 901 902 /* set sec props */ 903 secprops=make_secprops(minssf,maxssf); 904 905 if (secprops!=NULL) 906 result=sasl_setprop(conn, SASL_SEC_PROPS, secprops); 907 908 /* if not set throw and exception */ 909 if (result!=SASL_OK) 910 throwexception(env,result); 911} 912 913JNIEXPORT jint JNICALL Java_CyrusSasl_GenericCommon_jni_1sasl_1getSecurity 914 (JNIEnv *env, 915 jobject obj __attribute__((unused)), 916 jint ptr) 917{ 918 int r = SASL_FAIL; 919 sasl_conn_t *conn = (sasl_conn_t *) ptr; 920 int *ssfp; 921 922 r = sasl_getprop(conn, SASL_SSF, (const void **) &ssfp); 923 if (r != SASL_OK) { 924 throwexception(env, r); 925 } 926 927 return *ssfp; 928} 929 930 931