Fossil SCM
Merge from trunk.
Commit
e4a698bdd2fe73f65d299e0582574e4051e277d8
Parent
d244452bda788c3…
10 files changed
+1
+1
+10
-15
+17
-6
+1
-1
+9
-43
+51
-6
+2
-1
+2
-1
+10
-1
| --- compat/zlib/configure | ||
| +++ compat/zlib/configure | ||
| @@ -814,5 +814,6 @@ | ||
| 814 | 814 | /^mandir *=/s#=.*#=$mandir# |
| 815 | 815 | /^LDFLAGS *=/s#=.*#=$LDFLAGS# |
| 816 | 816 | " | sed -e " |
| 817 | 817 | s/\@VERSION\@/$VER/g; |
| 818 | 818 | " > zlib.pc |
| 819 | +# | |
| 819 | 820 |
| --- compat/zlib/configure | |
| +++ compat/zlib/configure | |
| @@ -814,5 +814,6 @@ | |
| 814 | /^mandir *=/s#=.*#=$mandir# |
| 815 | /^LDFLAGS *=/s#=.*#=$LDFLAGS# |
| 816 | " | sed -e " |
| 817 | s/\@VERSION\@/$VER/g; |
| 818 | " > zlib.pc |
| 819 |
| --- compat/zlib/configure | |
| +++ compat/zlib/configure | |
| @@ -814,5 +814,6 @@ | |
| 814 | /^mandir *=/s#=.*#=$mandir# |
| 815 | /^LDFLAGS *=/s#=.*#=$LDFLAGS# |
| 816 | " | sed -e " |
| 817 | s/\@VERSION\@/$VER/g; |
| 818 | " > zlib.pc |
| 819 | # |
| 820 |
| --- compat/zlib/configure | ||
| +++ compat/zlib/configure | ||
| @@ -814,5 +814,6 @@ | ||
| 814 | 814 | /^mandir *=/s#=.*#=$mandir# |
| 815 | 815 | /^LDFLAGS *=/s#=.*#=$LDFLAGS# |
| 816 | 816 | " | sed -e " |
| 817 | 817 | s/\@VERSION\@/$VER/g; |
| 818 | 818 | " > zlib.pc |
| 819 | +# | |
| 819 | 820 |
| --- compat/zlib/configure | |
| +++ compat/zlib/configure | |
| @@ -814,5 +814,6 @@ | |
| 814 | /^mandir *=/s#=.*#=$mandir# |
| 815 | /^LDFLAGS *=/s#=.*#=$LDFLAGS# |
| 816 | " | sed -e " |
| 817 | s/\@VERSION\@/$VER/g; |
| 818 | " > zlib.pc |
| 819 |
| --- compat/zlib/configure | |
| +++ compat/zlib/configure | |
| @@ -814,5 +814,6 @@ | |
| 814 | /^mandir *=/s#=.*#=$mandir# |
| 815 | /^LDFLAGS *=/s#=.*#=$LDFLAGS# |
| 816 | " | sed -e " |
| 817 | s/\@VERSION\@/$VER/g; |
| 818 | " > zlib.pc |
| 819 | # |
| 820 |
+10
-15
| --- src/blob.c | ||
| +++ src/blob.c | ||
| @@ -1104,26 +1104,21 @@ | ||
| 1104 | 1104 | blob_zero(&temp); |
| 1105 | 1105 | blob_append(&temp, zUtf8, -1); |
| 1106 | 1106 | blob_swap(pBlob, &temp); |
| 1107 | 1107 | blob_reset(&temp); |
| 1108 | 1108 | #ifdef _WIN32 |
| 1109 | - }else if( starts_with_utf16le_bom(pBlob, &bomSize) ){ | |
| 1110 | - /* Make sure the blob contains two terminating 0-bytes */ | |
| 1111 | - blob_append(pBlob, "", 1); | |
| 1112 | - zUtf8 = blob_str(pBlob) + bomSize; | |
| 1113 | - zUtf8 = fossil_unicode_to_utf8(zUtf8); | |
| 1114 | - blob_zero(pBlob); | |
| 1115 | - blob_append(pBlob, zUtf8, -1); | |
| 1116 | - fossil_unicode_free(zUtf8); | |
| 1117 | - }else if( starts_with_utf16be_bom(pBlob, &bomSize) ){ | |
| 1118 | - unsigned int i = blob_size(pBlob); | |
| 1109 | + }else if( starts_with_utf16_bom(pBlob, &bomSize) ){ | |
| 1119 | 1110 | zUtf8 = blob_buffer(pBlob); |
| 1120 | - while( i > 0 ){ | |
| 1121 | - /* swap bytes of unicode representation */ | |
| 1122 | - char zTemp = zUtf8[--i]; | |
| 1123 | - zUtf8[i] = zUtf8[i-1]; | |
| 1124 | - zUtf8[--i] = zTemp; | |
| 1111 | + if (*((unsigned short *)zUtf8) == 0xfffe) { | |
| 1112 | + /* Found BOM, but with reversed bytes */ | |
| 1113 | + unsigned int i = blob_size(pBlob); | |
| 1114 | + while( i > 0 ){ | |
| 1115 | + /* swap bytes of unicode representation */ | |
| 1116 | + char zTemp = zUtf8[--i]; | |
| 1117 | + zUtf8[i] = zUtf8[i-1]; | |
| 1118 | + zUtf8[--i] = zTemp; | |
| 1119 | + } | |
| 1125 | 1120 | } |
| 1126 | 1121 | /* Make sure the blob contains two terminating 0-bytes */ |
| 1127 | 1122 | blob_append(pBlob, "", 1); |
| 1128 | 1123 | zUtf8 = blob_str(pBlob) + bomSize; |
| 1129 | 1124 | zUtf8 = fossil_unicode_to_utf8(zUtf8); |
| 1130 | 1125 |
| --- src/blob.c | |
| +++ src/blob.c | |
| @@ -1104,26 +1104,21 @@ | |
| 1104 | blob_zero(&temp); |
| 1105 | blob_append(&temp, zUtf8, -1); |
| 1106 | blob_swap(pBlob, &temp); |
| 1107 | blob_reset(&temp); |
| 1108 | #ifdef _WIN32 |
| 1109 | }else if( starts_with_utf16le_bom(pBlob, &bomSize) ){ |
| 1110 | /* Make sure the blob contains two terminating 0-bytes */ |
| 1111 | blob_append(pBlob, "", 1); |
| 1112 | zUtf8 = blob_str(pBlob) + bomSize; |
| 1113 | zUtf8 = fossil_unicode_to_utf8(zUtf8); |
| 1114 | blob_zero(pBlob); |
| 1115 | blob_append(pBlob, zUtf8, -1); |
| 1116 | fossil_unicode_free(zUtf8); |
| 1117 | }else if( starts_with_utf16be_bom(pBlob, &bomSize) ){ |
| 1118 | unsigned int i = blob_size(pBlob); |
| 1119 | zUtf8 = blob_buffer(pBlob); |
| 1120 | while( i > 0 ){ |
| 1121 | /* swap bytes of unicode representation */ |
| 1122 | char zTemp = zUtf8[--i]; |
| 1123 | zUtf8[i] = zUtf8[i-1]; |
| 1124 | zUtf8[--i] = zTemp; |
| 1125 | } |
| 1126 | /* Make sure the blob contains two terminating 0-bytes */ |
| 1127 | blob_append(pBlob, "", 1); |
| 1128 | zUtf8 = blob_str(pBlob) + bomSize; |
| 1129 | zUtf8 = fossil_unicode_to_utf8(zUtf8); |
| 1130 |
| --- src/blob.c | |
| +++ src/blob.c | |
| @@ -1104,26 +1104,21 @@ | |
| 1104 | blob_zero(&temp); |
| 1105 | blob_append(&temp, zUtf8, -1); |
| 1106 | blob_swap(pBlob, &temp); |
| 1107 | blob_reset(&temp); |
| 1108 | #ifdef _WIN32 |
| 1109 | }else if( starts_with_utf16_bom(pBlob, &bomSize) ){ |
| 1110 | zUtf8 = blob_buffer(pBlob); |
| 1111 | if (*((unsigned short *)zUtf8) == 0xfffe) { |
| 1112 | /* Found BOM, but with reversed bytes */ |
| 1113 | unsigned int i = blob_size(pBlob); |
| 1114 | while( i > 0 ){ |
| 1115 | /* swap bytes of unicode representation */ |
| 1116 | char zTemp = zUtf8[--i]; |
| 1117 | zUtf8[i] = zUtf8[i-1]; |
| 1118 | zUtf8[--i] = zTemp; |
| 1119 | } |
| 1120 | } |
| 1121 | /* Make sure the blob contains two terminating 0-bytes */ |
| 1122 | blob_append(pBlob, "", 1); |
| 1123 | zUtf8 = blob_str(pBlob) + bomSize; |
| 1124 | zUtf8 = fossil_unicode_to_utf8(zUtf8); |
| 1125 |
+17
-6
| --- src/checkin.c | ||
| +++ src/checkin.c | ||
| @@ -616,30 +616,36 @@ | ||
| 616 | 616 | ** of the array. |
| 617 | 617 | ** |
| 618 | 618 | ** If there were no arguments passed to [commit], aCommitFile is not |
| 619 | 619 | ** allocated and remains NULL. Other parts of the code interpret this |
| 620 | 620 | ** to mean "all files". |
| 621 | +** | |
| 622 | +** Returns 1 if there was a warning, 0 otherwise. | |
| 621 | 623 | */ |
| 622 | -void select_commit_files(void){ | |
| 624 | +int select_commit_files(void){ | |
| 625 | + int result = 0; | |
| 623 | 626 | if( g.argc>2 ){ |
| 624 | - int ii; | |
| 627 | + int ii, jj=0; | |
| 625 | 628 | Blob b; |
| 626 | 629 | blob_zero(&b); |
| 627 | 630 | g.aCommitFile = fossil_malloc(sizeof(int)*(g.argc-1)); |
| 628 | 631 | |
| 629 | 632 | for(ii=2; ii<g.argc; ii++){ |
| 630 | 633 | int iId; |
| 631 | 634 | file_tree_name(g.argv[ii], &b, 1); |
| 632 | 635 | iId = db_int(-1, "SELECT id FROM vfile WHERE pathname=%Q", blob_str(&b)); |
| 633 | 636 | if( iId<0 ){ |
| 634 | - fossil_fatal("fossil knows nothing about: %s", g.argv[ii]); | |
| 637 | + fossil_warning("fossil knows nothing about: %s", g.argv[ii]); | |
| 638 | + result = 1; | |
| 639 | + } else { | |
| 640 | + g.aCommitFile[jj++] = iId; | |
| 635 | 641 | } |
| 636 | - g.aCommitFile[ii-2] = iId; | |
| 637 | 642 | blob_reset(&b); |
| 638 | 643 | } |
| 639 | - g.aCommitFile[ii-2] = 0; | |
| 644 | + g.aCommitFile[jj] = 0; | |
| 640 | 645 | } |
| 646 | + return result; | |
| 641 | 647 | } |
| 642 | 648 | |
| 643 | 649 | /* |
| 644 | 650 | ** Make sure the current check-in with timestamp zDate is younger than its |
| 645 | 651 | ** ancestor identified rid and zUuid. Throw a fatal error if not. |
| @@ -1199,11 +1205,16 @@ | ||
| 1199 | 1205 | ** After the following function call has returned, the Global.aCommitFile[] |
| 1200 | 1206 | ** array is allocated to contain the "id" field from the vfile table |
| 1201 | 1207 | ** for each file to be committed. Or, if aCommitFile is NULL, all files |
| 1202 | 1208 | ** should be committed. |
| 1203 | 1209 | */ |
| 1204 | - select_commit_files(); | |
| 1210 | + if ( select_commit_files() ){ | |
| 1211 | + blob_zero(&ans); | |
| 1212 | + prompt_user("continue (y/N)? ", &ans); | |
| 1213 | + cReply = blob_str(&ans)[0]; | |
| 1214 | + if( cReply!='y' && cReply!='Y' ) fossil_exit(1);; | |
| 1215 | + } | |
| 1205 | 1216 | isAMerge = db_exists("SELECT 1 FROM vmerge WHERE id=0"); |
| 1206 | 1217 | if( g.aCommitFile && isAMerge ){ |
| 1207 | 1218 | fossil_fatal("cannot do a partial commit of a merge"); |
| 1208 | 1219 | } |
| 1209 | 1220 | |
| 1210 | 1221 |
| --- src/checkin.c | |
| +++ src/checkin.c | |
| @@ -616,30 +616,36 @@ | |
| 616 | ** of the array. |
| 617 | ** |
| 618 | ** If there were no arguments passed to [commit], aCommitFile is not |
| 619 | ** allocated and remains NULL. Other parts of the code interpret this |
| 620 | ** to mean "all files". |
| 621 | */ |
| 622 | void select_commit_files(void){ |
| 623 | if( g.argc>2 ){ |
| 624 | int ii; |
| 625 | Blob b; |
| 626 | blob_zero(&b); |
| 627 | g.aCommitFile = fossil_malloc(sizeof(int)*(g.argc-1)); |
| 628 | |
| 629 | for(ii=2; ii<g.argc; ii++){ |
| 630 | int iId; |
| 631 | file_tree_name(g.argv[ii], &b, 1); |
| 632 | iId = db_int(-1, "SELECT id FROM vfile WHERE pathname=%Q", blob_str(&b)); |
| 633 | if( iId<0 ){ |
| 634 | fossil_fatal("fossil knows nothing about: %s", g.argv[ii]); |
| 635 | } |
| 636 | g.aCommitFile[ii-2] = iId; |
| 637 | blob_reset(&b); |
| 638 | } |
| 639 | g.aCommitFile[ii-2] = 0; |
| 640 | } |
| 641 | } |
| 642 | |
| 643 | /* |
| 644 | ** Make sure the current check-in with timestamp zDate is younger than its |
| 645 | ** ancestor identified rid and zUuid. Throw a fatal error if not. |
| @@ -1199,11 +1205,16 @@ | |
| 1199 | ** After the following function call has returned, the Global.aCommitFile[] |
| 1200 | ** array is allocated to contain the "id" field from the vfile table |
| 1201 | ** for each file to be committed. Or, if aCommitFile is NULL, all files |
| 1202 | ** should be committed. |
| 1203 | */ |
| 1204 | select_commit_files(); |
| 1205 | isAMerge = db_exists("SELECT 1 FROM vmerge WHERE id=0"); |
| 1206 | if( g.aCommitFile && isAMerge ){ |
| 1207 | fossil_fatal("cannot do a partial commit of a merge"); |
| 1208 | } |
| 1209 | |
| 1210 |
| --- src/checkin.c | |
| +++ src/checkin.c | |
| @@ -616,30 +616,36 @@ | |
| 616 | ** of the array. |
| 617 | ** |
| 618 | ** If there were no arguments passed to [commit], aCommitFile is not |
| 619 | ** allocated and remains NULL. Other parts of the code interpret this |
| 620 | ** to mean "all files". |
| 621 | ** |
| 622 | ** Returns 1 if there was a warning, 0 otherwise. |
| 623 | */ |
| 624 | int select_commit_files(void){ |
| 625 | int result = 0; |
| 626 | if( g.argc>2 ){ |
| 627 | int ii, jj=0; |
| 628 | Blob b; |
| 629 | blob_zero(&b); |
| 630 | g.aCommitFile = fossil_malloc(sizeof(int)*(g.argc-1)); |
| 631 | |
| 632 | for(ii=2; ii<g.argc; ii++){ |
| 633 | int iId; |
| 634 | file_tree_name(g.argv[ii], &b, 1); |
| 635 | iId = db_int(-1, "SELECT id FROM vfile WHERE pathname=%Q", blob_str(&b)); |
| 636 | if( iId<0 ){ |
| 637 | fossil_warning("fossil knows nothing about: %s", g.argv[ii]); |
| 638 | result = 1; |
| 639 | } else { |
| 640 | g.aCommitFile[jj++] = iId; |
| 641 | } |
| 642 | blob_reset(&b); |
| 643 | } |
| 644 | g.aCommitFile[jj] = 0; |
| 645 | } |
| 646 | return result; |
| 647 | } |
| 648 | |
| 649 | /* |
| 650 | ** Make sure the current check-in with timestamp zDate is younger than its |
| 651 | ** ancestor identified rid and zUuid. Throw a fatal error if not. |
| @@ -1199,11 +1205,16 @@ | |
| 1205 | ** After the following function call has returned, the Global.aCommitFile[] |
| 1206 | ** array is allocated to contain the "id" field from the vfile table |
| 1207 | ** for each file to be committed. Or, if aCommitFile is NULL, all files |
| 1208 | ** should be committed. |
| 1209 | */ |
| 1210 | if ( select_commit_files() ){ |
| 1211 | blob_zero(&ans); |
| 1212 | prompt_user("continue (y/N)? ", &ans); |
| 1213 | cReply = blob_str(&ans)[0]; |
| 1214 | if( cReply!='y' && cReply!='Y' ) fossil_exit(1);; |
| 1215 | } |
| 1216 | isAMerge = db_exists("SELECT 1 FROM vmerge WHERE id=0"); |
| 1217 | if( g.aCommitFile && isAMerge ){ |
| 1218 | fossil_fatal("cannot do a partial commit of a merge"); |
| 1219 | } |
| 1220 | |
| 1221 |
+1
-1
| --- src/cson_amalgamation.c | ||
| +++ src/cson_amalgamation.c | ||
| @@ -4349,11 +4349,11 @@ | ||
| 4349 | 4349 | { |
| 4350 | 4350 | return 0; |
| 4351 | 4351 | } |
| 4352 | 4352 | else |
| 4353 | 4353 | { |
| 4354 | - unsigned char * x = (unsigned char *)realloc( buf->mem, n ); | |
| 4354 | + unsigned char * x = (unsigned char *)cson_realloc( buf->mem, n, "cson_buffer::mem" ); | |
| 4355 | 4355 | if( ! x ) return cson_rc.AllocError; |
| 4356 | 4356 | memset( x + buf->used, 0, n - buf->used ); |
| 4357 | 4357 | buf->mem = x; |
| 4358 | 4358 | buf->capacity = n; |
| 4359 | 4359 | ++buf->timesExpanded; |
| 4360 | 4360 |
| --- src/cson_amalgamation.c | |
| +++ src/cson_amalgamation.c | |
| @@ -4349,11 +4349,11 @@ | |
| 4349 | { |
| 4350 | return 0; |
| 4351 | } |
| 4352 | else |
| 4353 | { |
| 4354 | unsigned char * x = (unsigned char *)realloc( buf->mem, n ); |
| 4355 | if( ! x ) return cson_rc.AllocError; |
| 4356 | memset( x + buf->used, 0, n - buf->used ); |
| 4357 | buf->mem = x; |
| 4358 | buf->capacity = n; |
| 4359 | ++buf->timesExpanded; |
| 4360 |
| --- src/cson_amalgamation.c | |
| +++ src/cson_amalgamation.c | |
| @@ -4349,11 +4349,11 @@ | |
| 4349 | { |
| 4350 | return 0; |
| 4351 | } |
| 4352 | else |
| 4353 | { |
| 4354 | unsigned char * x = (unsigned char *)cson_realloc( buf->mem, n, "cson_buffer::mem" ); |
| 4355 | if( ! x ) return cson_rc.AllocError; |
| 4356 | memset( x + buf->used, 0, n - buf->used ); |
| 4357 | buf->mem = x; |
| 4358 | buf->capacity = n; |
| 4359 | ++buf->timesExpanded; |
| 4360 |
+9
-43
| --- src/diff.c | ||
| +++ src/diff.c | ||
| @@ -359,53 +359,19 @@ | ||
| 359 | 359 | ** This function returns non-zero if the blob starts with a UTF-16le or |
| 360 | 360 | ** UTF-16be byte-order-mark (BOM). |
| 361 | 361 | */ |
| 362 | 362 | int starts_with_utf16_bom(const Blob *pContent, int *pnByte){ |
| 363 | 363 | const char *z = blob_buffer(pContent); |
| 364 | - int c1, c2; | |
| 365 | - | |
| 366 | - if( pnByte ) *pnByte = 2; | |
| 367 | - if( blob_size(pContent)<2 ) return 0; | |
| 368 | - c1 = z[0]; c2 = z[1]; | |
| 369 | - if( (c1==(char)0xff) && (c2==(char)0xfe) ){ | |
| 370 | - return 1; | |
| 371 | - }else if( (c1==(char)0xfe) && (c2==(char)0xff) ){ | |
| 372 | - return 1; | |
| 373 | - } | |
| 374 | - return 0; | |
| 375 | -} | |
| 376 | - | |
| 377 | -/* | |
| 378 | -** This function returns non-zero if the blob starts with a UTF-16le | |
| 379 | -** byte-order-mark (BOM). | |
| 380 | -*/ | |
| 381 | -int starts_with_utf16le_bom(const Blob *pContent, int *pnByte){ | |
| 382 | - const char *z = blob_buffer(pContent); | |
| 383 | - int c1, c2; | |
| 384 | - | |
| 385 | - if( pnByte ) *pnByte = 2; | |
| 386 | - if( blob_size(pContent)<2 ) return 0; | |
| 387 | - c1 = z[0]; c2 = z[1]; | |
| 388 | - if( (c1==(char)0xff) && (c2==(char)0xfe) ){ | |
| 389 | - return 1; | |
| 390 | - } | |
| 391 | - return 0; | |
| 392 | -} | |
| 393 | - | |
| 394 | -/* | |
| 395 | -** This function returns non-zero if the blob starts with a UTF-16be | |
| 396 | -** byte-order-mark (BOM). | |
| 397 | -*/ | |
| 398 | -int starts_with_utf16be_bom(const Blob *pContent, int *pnByte){ | |
| 399 | - const char *z = blob_buffer(pContent); | |
| 400 | - int c1, c2; | |
| 401 | - | |
| 402 | - if( pnByte ) *pnByte = 2; | |
| 403 | - if( blob_size(pContent)<2 ) return 0; | |
| 404 | - c1 = z[0]; c2 = z[1]; | |
| 405 | - if( (c1==(char)0xfe) && (c2==(char)0xff) ){ | |
| 406 | - return 1; | |
| 364 | + int c1; | |
| 365 | + | |
| 366 | + if( pnByte ) *pnByte = 2; | |
| 367 | + if( (blob_size(pContent)<2) || (blob_size(pContent)&1)) return 0; | |
| 368 | + c1 = ((unsigned short *)z)[0]; | |
| 369 | + if( (c1==0xfeff) || (c1==0xfffe) ){ | |
| 370 | + if( blob_size(pContent) < 4 ) return 1; | |
| 371 | + c1 = ((unsigned short *)z)[1]; | |
| 372 | + if( c1 != 0 ) return 1; | |
| 407 | 373 | } |
| 408 | 374 | return 0; |
| 409 | 375 | } |
| 410 | 376 | |
| 411 | 377 | /* |
| 412 | 378 |
| --- src/diff.c | |
| +++ src/diff.c | |
| @@ -359,53 +359,19 @@ | |
| 359 | ** This function returns non-zero if the blob starts with a UTF-16le or |
| 360 | ** UTF-16be byte-order-mark (BOM). |
| 361 | */ |
| 362 | int starts_with_utf16_bom(const Blob *pContent, int *pnByte){ |
| 363 | const char *z = blob_buffer(pContent); |
| 364 | int c1, c2; |
| 365 | |
| 366 | if( pnByte ) *pnByte = 2; |
| 367 | if( blob_size(pContent)<2 ) return 0; |
| 368 | c1 = z[0]; c2 = z[1]; |
| 369 | if( (c1==(char)0xff) && (c2==(char)0xfe) ){ |
| 370 | return 1; |
| 371 | }else if( (c1==(char)0xfe) && (c2==(char)0xff) ){ |
| 372 | return 1; |
| 373 | } |
| 374 | return 0; |
| 375 | } |
| 376 | |
| 377 | /* |
| 378 | ** This function returns non-zero if the blob starts with a UTF-16le |
| 379 | ** byte-order-mark (BOM). |
| 380 | */ |
| 381 | int starts_with_utf16le_bom(const Blob *pContent, int *pnByte){ |
| 382 | const char *z = blob_buffer(pContent); |
| 383 | int c1, c2; |
| 384 | |
| 385 | if( pnByte ) *pnByte = 2; |
| 386 | if( blob_size(pContent)<2 ) return 0; |
| 387 | c1 = z[0]; c2 = z[1]; |
| 388 | if( (c1==(char)0xff) && (c2==(char)0xfe) ){ |
| 389 | return 1; |
| 390 | } |
| 391 | return 0; |
| 392 | } |
| 393 | |
| 394 | /* |
| 395 | ** This function returns non-zero if the blob starts with a UTF-16be |
| 396 | ** byte-order-mark (BOM). |
| 397 | */ |
| 398 | int starts_with_utf16be_bom(const Blob *pContent, int *pnByte){ |
| 399 | const char *z = blob_buffer(pContent); |
| 400 | int c1, c2; |
| 401 | |
| 402 | if( pnByte ) *pnByte = 2; |
| 403 | if( blob_size(pContent)<2 ) return 0; |
| 404 | c1 = z[0]; c2 = z[1]; |
| 405 | if( (c1==(char)0xfe) && (c2==(char)0xff) ){ |
| 406 | return 1; |
| 407 | } |
| 408 | return 0; |
| 409 | } |
| 410 | |
| 411 | /* |
| 412 |
| --- src/diff.c | |
| +++ src/diff.c | |
| @@ -359,53 +359,19 @@ | |
| 359 | ** This function returns non-zero if the blob starts with a UTF-16le or |
| 360 | ** UTF-16be byte-order-mark (BOM). |
| 361 | */ |
| 362 | int starts_with_utf16_bom(const Blob *pContent, int *pnByte){ |
| 363 | const char *z = blob_buffer(pContent); |
| 364 | int c1; |
| 365 | |
| 366 | if( pnByte ) *pnByte = 2; |
| 367 | if( (blob_size(pContent)<2) || (blob_size(pContent)&1)) return 0; |
| 368 | c1 = ((unsigned short *)z)[0]; |
| 369 | if( (c1==0xfeff) || (c1==0xfffe) ){ |
| 370 | if( blob_size(pContent) < 4 ) return 1; |
| 371 | c1 = ((unsigned short *)z)[1]; |
| 372 | if( c1 != 0 ) return 1; |
| 373 | } |
| 374 | return 0; |
| 375 | } |
| 376 | |
| 377 | /* |
| 378 |
+51
-6
| --- src/http_transport.c | ||
| +++ src/http_transport.c | ||
| @@ -183,10 +183,11 @@ | ||
| 183 | 183 | ** and run an SSH command to talk to the remote machine. |
| 184 | 184 | */ |
| 185 | 185 | const char *zSsh; /* The base SSH command */ |
| 186 | 186 | Blob zCmd; /* The SSH command */ |
| 187 | 187 | char *zHost; /* The host name to contact */ |
| 188 | + int n; /* Size of prefix string */ | |
| 188 | 189 | |
| 189 | 190 | zSsh = db_get("ssh-command", zDefaultSshCmd); |
| 190 | 191 | blob_init(&zCmd, zSsh, -1); |
| 191 | 192 | if( g.urlPort!=g.urlDfltPort ){ |
| 192 | 193 | #ifdef __MINGW32__ |
| @@ -219,22 +220,63 @@ | ||
| 219 | 220 | } |
| 220 | 221 | #endif |
| 221 | 222 | }else{ |
| 222 | 223 | zHost = mprintf("%s", g.urlName); |
| 223 | 224 | } |
| 225 | + n = blob_size(&zCmd); | |
| 224 | 226 | blob_append(&zCmd, " ", 1); |
| 225 | 227 | shell_escape(&zCmd, zHost); |
| 226 | - fossil_print(" %s\n", zHost); /* Show the conclusion of the SSH command */ | |
| 228 | + if( g.urlShell ){ | |
| 229 | + blob_appendf(&zCmd, " %s", g.urlShell); | |
| 230 | + }else{ | |
| 231 | +#if defined(FOSSIL_ENABLE_SSH_FAR_SIDE) | |
| 232 | + /* The following works. But only if the fossil on the remote side | |
| 233 | + ** is recent enough to support the test-ssh-far-side command. That | |
| 234 | + ** command was added on 2013-02-06. We will leave this turned off | |
| 235 | + ** until most fossil servers have upgraded to that version or a later | |
| 236 | + ** version. The sync will still work as long as the shell on the far | |
| 237 | + ** side is bash and not tcsh. And if the default far side shell is | |
| 238 | + ** tcsh, then the shell=/bin/bash query parameter can be used as a | |
| 239 | + ** work-around. Enable this code after about a year... | |
| 240 | + */ | |
| 241 | + blob_appendf(&zCmd, " exec %s test-ssh-far-side", g.urlFossil); | |
| 242 | +#endif | |
| 243 | + } | |
| 244 | + fossil_print("%s\n", blob_str(&zCmd)+n); /* Show tail of SSH command */ | |
| 227 | 245 | free(zHost); |
| 228 | 246 | popen2(blob_str(&zCmd), &sshIn, &sshOut, &sshPid); |
| 229 | 247 | if( sshPid==0 ){ |
| 230 | 248 | fossil_fatal("cannot start ssh tunnel using [%b]", &zCmd); |
| 231 | 249 | } |
| 232 | 250 | blob_reset(&zCmd); |
| 233 | 251 | transport_ssh_startup(); |
| 234 | 252 | } |
| 235 | 253 | } |
| 254 | + | |
| 255 | +/* | |
| 256 | +** COMMAND: test-ssh-far-side | |
| 257 | +** | |
| 258 | +** Read lines of input text, one by one, and evaluate each line using | |
| 259 | +** system(). The ssh: sync protocol uses this on the far side of the | |
| 260 | +** SSH link. | |
| 261 | +*/ | |
| 262 | +void test_ssh_far_side_cmd(void){ | |
| 263 | + int i = 0; | |
| 264 | + int got; | |
| 265 | + char zLine[5000]; | |
| 266 | + while( i<sizeof(zLine) ){ | |
| 267 | + got = read(0, zLine+i, 1); | |
| 268 | + if( got==0 ) return; | |
| 269 | + if( zLine[i]=='\n' ){ | |
| 270 | + zLine[i] = 0; | |
| 271 | + system(zLine); | |
| 272 | + i = 0; | |
| 273 | + }else{ | |
| 274 | + i++; | |
| 275 | + } | |
| 276 | + } | |
| 277 | +} | |
| 236 | 278 | |
| 237 | 279 | /* |
| 238 | 280 | ** Open a connection to the server. The server is defined by the following |
| 239 | 281 | ** global variables: |
| 240 | 282 | ** |
| @@ -251,13 +293,13 @@ | ||
| 251 | 293 | Blob cmd; |
| 252 | 294 | blob_zero(&cmd); |
| 253 | 295 | shell_escape(&cmd, g.urlFossil); |
| 254 | 296 | blob_append(&cmd, " test-http ", -1); |
| 255 | 297 | shell_escape(&cmd, g.urlPath); |
| 256 | - /* printf("%s\n", blob_str(&cmd)); fflush(stdout); */ | |
| 257 | - fprintf(sshOut, "%s\n", blob_str(&cmd)); | |
| 298 | + fprintf(sshOut, "%s || true\n", blob_str(&cmd)); | |
| 258 | 299 | fflush(sshOut); |
| 300 | + if( g.fSshTrace ) printf("Sent: [%s]\n", blob_str(&cmd)); | |
| 259 | 301 | blob_reset(&cmd); |
| 260 | 302 | }else if( g.urlIsHttps ){ |
| 261 | 303 | #ifdef FOSSIL_ENABLE_SSL |
| 262 | 304 | rc = ssl_open(); |
| 263 | 305 | if( rc==0 ) transport.isOpen = 1; |
| @@ -403,11 +445,10 @@ | ||
| 403 | 445 | int got; |
| 404 | 446 | if( sshIn ){ |
| 405 | 447 | int x; |
| 406 | 448 | int wanted = N; |
| 407 | 449 | got = 0; |
| 408 | - /* printf("want %d bytes...\n", wanted); fflush(stdout); */ | |
| 409 | 450 | while( wanted>0 ){ |
| 410 | 451 | x = read(sshIn, &zBuf[got], wanted); |
| 411 | 452 | if( x<=0 ) break; |
| 412 | 453 | got += x; |
| 413 | 454 | wanted -= x; |
| @@ -438,11 +479,14 @@ | ||
| 438 | 479 | int transport_receive(char *zBuf, int N){ |
| 439 | 480 | int onHand; /* Bytes current held in the transport buffer */ |
| 440 | 481 | int nByte = 0; /* Bytes of content received */ |
| 441 | 482 | |
| 442 | 483 | onHand = transport.nUsed - transport.iCursor; |
| 443 | - /* printf("request %d with %d on hand\n", N, onHand); fflush(stdout); */ | |
| 484 | + if( g.fSshTrace){ | |
| 485 | + printf("Reading %d bytes with %d on hand... ", N, onHand); | |
| 486 | + fflush(stdout); | |
| 487 | + } | |
| 444 | 488 | if( onHand>0 ){ |
| 445 | 489 | int toMove = onHand; |
| 446 | 490 | if( toMove>N ) toMove = N; |
| 447 | 491 | /* printf("bytes on hand: %d of %d\n", toMove, N); fflush(stdout); */ |
| 448 | 492 | memcpy(zBuf, &transport.pBuf[transport.iCursor], toMove); |
| @@ -460,10 +504,11 @@ | ||
| 460 | 504 | if( got>0 ){ |
| 461 | 505 | nByte += got; |
| 462 | 506 | transport.nRcvd += got; |
| 463 | 507 | } |
| 464 | 508 | } |
| 509 | + if( g.fSshTrace ) printf("Got %d bytes\n", nByte); | |
| 465 | 510 | return nByte; |
| 466 | 511 | } |
| 467 | 512 | |
| 468 | 513 | /* |
| 469 | 514 | ** Load up to N new bytes of content into the transport.pBuf buffer. |
| @@ -532,11 +577,11 @@ | ||
| 532 | 577 | } |
| 533 | 578 | break; |
| 534 | 579 | } |
| 535 | 580 | i++; |
| 536 | 581 | } |
| 537 | - /* printf("Got line: [%s]\n", &transport.pBuf[iStart]); */ | |
| 582 | + if( g.fSshTrace ) printf("Got line: [%s]\n", &transport.pBuf[iStart]); | |
| 538 | 583 | return &transport.pBuf[iStart]; |
| 539 | 584 | } |
| 540 | 585 | |
| 541 | 586 | void transport_global_shutdown(void){ |
| 542 | 587 | if( g.urlIsSsh && sshPid ){ |
| 543 | 588 |
| --- src/http_transport.c | |
| +++ src/http_transport.c | |
| @@ -183,10 +183,11 @@ | |
| 183 | ** and run an SSH command to talk to the remote machine. |
| 184 | */ |
| 185 | const char *zSsh; /* The base SSH command */ |
| 186 | Blob zCmd; /* The SSH command */ |
| 187 | char *zHost; /* The host name to contact */ |
| 188 | |
| 189 | zSsh = db_get("ssh-command", zDefaultSshCmd); |
| 190 | blob_init(&zCmd, zSsh, -1); |
| 191 | if( g.urlPort!=g.urlDfltPort ){ |
| 192 | #ifdef __MINGW32__ |
| @@ -219,22 +220,63 @@ | |
| 219 | } |
| 220 | #endif |
| 221 | }else{ |
| 222 | zHost = mprintf("%s", g.urlName); |
| 223 | } |
| 224 | blob_append(&zCmd, " ", 1); |
| 225 | shell_escape(&zCmd, zHost); |
| 226 | fossil_print(" %s\n", zHost); /* Show the conclusion of the SSH command */ |
| 227 | free(zHost); |
| 228 | popen2(blob_str(&zCmd), &sshIn, &sshOut, &sshPid); |
| 229 | if( sshPid==0 ){ |
| 230 | fossil_fatal("cannot start ssh tunnel using [%b]", &zCmd); |
| 231 | } |
| 232 | blob_reset(&zCmd); |
| 233 | transport_ssh_startup(); |
| 234 | } |
| 235 | } |
| 236 | |
| 237 | /* |
| 238 | ** Open a connection to the server. The server is defined by the following |
| 239 | ** global variables: |
| 240 | ** |
| @@ -251,13 +293,13 @@ | |
| 251 | Blob cmd; |
| 252 | blob_zero(&cmd); |
| 253 | shell_escape(&cmd, g.urlFossil); |
| 254 | blob_append(&cmd, " test-http ", -1); |
| 255 | shell_escape(&cmd, g.urlPath); |
| 256 | /* printf("%s\n", blob_str(&cmd)); fflush(stdout); */ |
| 257 | fprintf(sshOut, "%s\n", blob_str(&cmd)); |
| 258 | fflush(sshOut); |
| 259 | blob_reset(&cmd); |
| 260 | }else if( g.urlIsHttps ){ |
| 261 | #ifdef FOSSIL_ENABLE_SSL |
| 262 | rc = ssl_open(); |
| 263 | if( rc==0 ) transport.isOpen = 1; |
| @@ -403,11 +445,10 @@ | |
| 403 | int got; |
| 404 | if( sshIn ){ |
| 405 | int x; |
| 406 | int wanted = N; |
| 407 | got = 0; |
| 408 | /* printf("want %d bytes...\n", wanted); fflush(stdout); */ |
| 409 | while( wanted>0 ){ |
| 410 | x = read(sshIn, &zBuf[got], wanted); |
| 411 | if( x<=0 ) break; |
| 412 | got += x; |
| 413 | wanted -= x; |
| @@ -438,11 +479,14 @@ | |
| 438 | int transport_receive(char *zBuf, int N){ |
| 439 | int onHand; /* Bytes current held in the transport buffer */ |
| 440 | int nByte = 0; /* Bytes of content received */ |
| 441 | |
| 442 | onHand = transport.nUsed - transport.iCursor; |
| 443 | /* printf("request %d with %d on hand\n", N, onHand); fflush(stdout); */ |
| 444 | if( onHand>0 ){ |
| 445 | int toMove = onHand; |
| 446 | if( toMove>N ) toMove = N; |
| 447 | /* printf("bytes on hand: %d of %d\n", toMove, N); fflush(stdout); */ |
| 448 | memcpy(zBuf, &transport.pBuf[transport.iCursor], toMove); |
| @@ -460,10 +504,11 @@ | |
| 460 | if( got>0 ){ |
| 461 | nByte += got; |
| 462 | transport.nRcvd += got; |
| 463 | } |
| 464 | } |
| 465 | return nByte; |
| 466 | } |
| 467 | |
| 468 | /* |
| 469 | ** Load up to N new bytes of content into the transport.pBuf buffer. |
| @@ -532,11 +577,11 @@ | |
| 532 | } |
| 533 | break; |
| 534 | } |
| 535 | i++; |
| 536 | } |
| 537 | /* printf("Got line: [%s]\n", &transport.pBuf[iStart]); */ |
| 538 | return &transport.pBuf[iStart]; |
| 539 | } |
| 540 | |
| 541 | void transport_global_shutdown(void){ |
| 542 | if( g.urlIsSsh && sshPid ){ |
| 543 |
| --- src/http_transport.c | |
| +++ src/http_transport.c | |
| @@ -183,10 +183,11 @@ | |
| 183 | ** and run an SSH command to talk to the remote machine. |
| 184 | */ |
| 185 | const char *zSsh; /* The base SSH command */ |
| 186 | Blob zCmd; /* The SSH command */ |
| 187 | char *zHost; /* The host name to contact */ |
| 188 | int n; /* Size of prefix string */ |
| 189 | |
| 190 | zSsh = db_get("ssh-command", zDefaultSshCmd); |
| 191 | blob_init(&zCmd, zSsh, -1); |
| 192 | if( g.urlPort!=g.urlDfltPort ){ |
| 193 | #ifdef __MINGW32__ |
| @@ -219,22 +220,63 @@ | |
| 220 | } |
| 221 | #endif |
| 222 | }else{ |
| 223 | zHost = mprintf("%s", g.urlName); |
| 224 | } |
| 225 | n = blob_size(&zCmd); |
| 226 | blob_append(&zCmd, " ", 1); |
| 227 | shell_escape(&zCmd, zHost); |
| 228 | if( g.urlShell ){ |
| 229 | blob_appendf(&zCmd, " %s", g.urlShell); |
| 230 | }else{ |
| 231 | #if defined(FOSSIL_ENABLE_SSH_FAR_SIDE) |
| 232 | /* The following works. But only if the fossil on the remote side |
| 233 | ** is recent enough to support the test-ssh-far-side command. That |
| 234 | ** command was added on 2013-02-06. We will leave this turned off |
| 235 | ** until most fossil servers have upgraded to that version or a later |
| 236 | ** version. The sync will still work as long as the shell on the far |
| 237 | ** side is bash and not tcsh. And if the default far side shell is |
| 238 | ** tcsh, then the shell=/bin/bash query parameter can be used as a |
| 239 | ** work-around. Enable this code after about a year... |
| 240 | */ |
| 241 | blob_appendf(&zCmd, " exec %s test-ssh-far-side", g.urlFossil); |
| 242 | #endif |
| 243 | } |
| 244 | fossil_print("%s\n", blob_str(&zCmd)+n); /* Show tail of SSH command */ |
| 245 | free(zHost); |
| 246 | popen2(blob_str(&zCmd), &sshIn, &sshOut, &sshPid); |
| 247 | if( sshPid==0 ){ |
| 248 | fossil_fatal("cannot start ssh tunnel using [%b]", &zCmd); |
| 249 | } |
| 250 | blob_reset(&zCmd); |
| 251 | transport_ssh_startup(); |
| 252 | } |
| 253 | } |
| 254 | |
| 255 | /* |
| 256 | ** COMMAND: test-ssh-far-side |
| 257 | ** |
| 258 | ** Read lines of input text, one by one, and evaluate each line using |
| 259 | ** system(). The ssh: sync protocol uses this on the far side of the |
| 260 | ** SSH link. |
| 261 | */ |
| 262 | void test_ssh_far_side_cmd(void){ |
| 263 | int i = 0; |
| 264 | int got; |
| 265 | char zLine[5000]; |
| 266 | while( i<sizeof(zLine) ){ |
| 267 | got = read(0, zLine+i, 1); |
| 268 | if( got==0 ) return; |
| 269 | if( zLine[i]=='\n' ){ |
| 270 | zLine[i] = 0; |
| 271 | system(zLine); |
| 272 | i = 0; |
| 273 | }else{ |
| 274 | i++; |
| 275 | } |
| 276 | } |
| 277 | } |
| 278 | |
| 279 | /* |
| 280 | ** Open a connection to the server. The server is defined by the following |
| 281 | ** global variables: |
| 282 | ** |
| @@ -251,13 +293,13 @@ | |
| 293 | Blob cmd; |
| 294 | blob_zero(&cmd); |
| 295 | shell_escape(&cmd, g.urlFossil); |
| 296 | blob_append(&cmd, " test-http ", -1); |
| 297 | shell_escape(&cmd, g.urlPath); |
| 298 | fprintf(sshOut, "%s || true\n", blob_str(&cmd)); |
| 299 | fflush(sshOut); |
| 300 | if( g.fSshTrace ) printf("Sent: [%s]\n", blob_str(&cmd)); |
| 301 | blob_reset(&cmd); |
| 302 | }else if( g.urlIsHttps ){ |
| 303 | #ifdef FOSSIL_ENABLE_SSL |
| 304 | rc = ssl_open(); |
| 305 | if( rc==0 ) transport.isOpen = 1; |
| @@ -403,11 +445,10 @@ | |
| 445 | int got; |
| 446 | if( sshIn ){ |
| 447 | int x; |
| 448 | int wanted = N; |
| 449 | got = 0; |
| 450 | while( wanted>0 ){ |
| 451 | x = read(sshIn, &zBuf[got], wanted); |
| 452 | if( x<=0 ) break; |
| 453 | got += x; |
| 454 | wanted -= x; |
| @@ -438,11 +479,14 @@ | |
| 479 | int transport_receive(char *zBuf, int N){ |
| 480 | int onHand; /* Bytes current held in the transport buffer */ |
| 481 | int nByte = 0; /* Bytes of content received */ |
| 482 | |
| 483 | onHand = transport.nUsed - transport.iCursor; |
| 484 | if( g.fSshTrace){ |
| 485 | printf("Reading %d bytes with %d on hand... ", N, onHand); |
| 486 | fflush(stdout); |
| 487 | } |
| 488 | if( onHand>0 ){ |
| 489 | int toMove = onHand; |
| 490 | if( toMove>N ) toMove = N; |
| 491 | /* printf("bytes on hand: %d of %d\n", toMove, N); fflush(stdout); */ |
| 492 | memcpy(zBuf, &transport.pBuf[transport.iCursor], toMove); |
| @@ -460,10 +504,11 @@ | |
| 504 | if( got>0 ){ |
| 505 | nByte += got; |
| 506 | transport.nRcvd += got; |
| 507 | } |
| 508 | } |
| 509 | if( g.fSshTrace ) printf("Got %d bytes\n", nByte); |
| 510 | return nByte; |
| 511 | } |
| 512 | |
| 513 | /* |
| 514 | ** Load up to N new bytes of content into the transport.pBuf buffer. |
| @@ -532,11 +577,11 @@ | |
| 577 | } |
| 578 | break; |
| 579 | } |
| 580 | i++; |
| 581 | } |
| 582 | if( g.fSshTrace ) printf("Got line: [%s]\n", &transport.pBuf[iStart]); |
| 583 | return &transport.pBuf[iStart]; |
| 584 | } |
| 585 | |
| 586 | void transport_global_shutdown(void){ |
| 587 | if( g.urlIsSsh && sshPid ){ |
| 588 |
+2
-1
| --- src/main.c | ||
| +++ src/main.c | ||
| @@ -171,11 +171,12 @@ | ||
| 171 | 171 | char *urlPath; /* Pathname for http: */ |
| 172 | 172 | char *urlUser; /* User id for http: */ |
| 173 | 173 | char *urlPasswd; /* Password for http: */ |
| 174 | 174 | char *urlCanonical; /* Canonical representation of the URL */ |
| 175 | 175 | char *urlProxyAuth; /* Proxy-Authorizer: string */ |
| 176 | - char *urlFossil; /* The path of the ?fossil=path suffix on ssh: */ | |
| 176 | + char *urlFossil; /* The fossil query parameter on ssh: */ | |
| 177 | + char *urlShell; /* The shell query parameter on ssh: */ | |
| 177 | 178 | int dontKeepUrl; /* Do not persist the URL */ |
| 178 | 179 | |
| 179 | 180 | const char *zLogin; /* Login name. "" if not logged in. */ |
| 180 | 181 | const char *zSSLIdentity; /* Value of --ssl-identity option, filename of SSL client identity */ |
| 181 | 182 | int useLocalauth; /* No login required if from 127.0.0.1 */ |
| 182 | 183 |
| --- src/main.c | |
| +++ src/main.c | |
| @@ -171,11 +171,12 @@ | |
| 171 | char *urlPath; /* Pathname for http: */ |
| 172 | char *urlUser; /* User id for http: */ |
| 173 | char *urlPasswd; /* Password for http: */ |
| 174 | char *urlCanonical; /* Canonical representation of the URL */ |
| 175 | char *urlProxyAuth; /* Proxy-Authorizer: string */ |
| 176 | char *urlFossil; /* The path of the ?fossil=path suffix on ssh: */ |
| 177 | int dontKeepUrl; /* Do not persist the URL */ |
| 178 | |
| 179 | const char *zLogin; /* Login name. "" if not logged in. */ |
| 180 | const char *zSSLIdentity; /* Value of --ssl-identity option, filename of SSL client identity */ |
| 181 | int useLocalauth; /* No login required if from 127.0.0.1 */ |
| 182 |
| --- src/main.c | |
| +++ src/main.c | |
| @@ -171,11 +171,12 @@ | |
| 171 | char *urlPath; /* Pathname for http: */ |
| 172 | char *urlUser; /* User id for http: */ |
| 173 | char *urlPasswd; /* Password for http: */ |
| 174 | char *urlCanonical; /* Canonical representation of the URL */ |
| 175 | char *urlProxyAuth; /* Proxy-Authorizer: string */ |
| 176 | char *urlFossil; /* The fossil query parameter on ssh: */ |
| 177 | char *urlShell; /* The shell query parameter on ssh: */ |
| 178 | int dontKeepUrl; /* Do not persist the URL */ |
| 179 | |
| 180 | const char *zLogin; /* Login name. "" if not logged in. */ |
| 181 | const char *zSSLIdentity; /* Value of --ssl-identity option, filename of SSL client identity */ |
| 182 | int useLocalauth; /* No login required if from 127.0.0.1 */ |
| 183 |
+2
-1
| --- src/main.c | ||
| +++ src/main.c | ||
| @@ -171,11 +171,12 @@ | ||
| 171 | 171 | char *urlPath; /* Pathname for http: */ |
| 172 | 172 | char *urlUser; /* User id for http: */ |
| 173 | 173 | char *urlPasswd; /* Password for http: */ |
| 174 | 174 | char *urlCanonical; /* Canonical representation of the URL */ |
| 175 | 175 | char *urlProxyAuth; /* Proxy-Authorizer: string */ |
| 176 | - char *urlFossil; /* The path of the ?fossil=path suffix on ssh: */ | |
| 176 | + char *urlFossil; /* The fossil query parameter on ssh: */ | |
| 177 | + char *urlShell; /* The shell query parameter on ssh: */ | |
| 177 | 178 | int dontKeepUrl; /* Do not persist the URL */ |
| 178 | 179 | |
| 179 | 180 | const char *zLogin; /* Login name. "" if not logged in. */ |
| 180 | 181 | const char *zSSLIdentity; /* Value of --ssl-identity option, filename of SSL client identity */ |
| 181 | 182 | int useLocalauth; /* No login required if from 127.0.0.1 */ |
| 182 | 183 |
| --- src/main.c | |
| +++ src/main.c | |
| @@ -171,11 +171,12 @@ | |
| 171 | char *urlPath; /* Pathname for http: */ |
| 172 | char *urlUser; /* User id for http: */ |
| 173 | char *urlPasswd; /* Password for http: */ |
| 174 | char *urlCanonical; /* Canonical representation of the URL */ |
| 175 | char *urlProxyAuth; /* Proxy-Authorizer: string */ |
| 176 | char *urlFossil; /* The path of the ?fossil=path suffix on ssh: */ |
| 177 | int dontKeepUrl; /* Do not persist the URL */ |
| 178 | |
| 179 | const char *zLogin; /* Login name. "" if not logged in. */ |
| 180 | const char *zSSLIdentity; /* Value of --ssl-identity option, filename of SSL client identity */ |
| 181 | int useLocalauth; /* No login required if from 127.0.0.1 */ |
| 182 |
| --- src/main.c | |
| +++ src/main.c | |
| @@ -171,11 +171,12 @@ | |
| 171 | char *urlPath; /* Pathname for http: */ |
| 172 | char *urlUser; /* User id for http: */ |
| 173 | char *urlPasswd; /* Password for http: */ |
| 174 | char *urlCanonical; /* Canonical representation of the URL */ |
| 175 | char *urlProxyAuth; /* Proxy-Authorizer: string */ |
| 176 | char *urlFossil; /* The fossil query parameter on ssh: */ |
| 177 | char *urlShell; /* The shell query parameter on ssh: */ |
| 178 | int dontKeepUrl; /* Do not persist the URL */ |
| 179 | |
| 180 | const char *zLogin; /* Login name. "" if not logged in. */ |
| 181 | const char *zSSLIdentity; /* Value of --ssl-identity option, filename of SSL client identity */ |
| 182 | int useLocalauth; /* No login required if from 127.0.0.1 */ |
| 183 |
+10
-1
| --- src/url.c | ||
| +++ src/url.c | ||
| @@ -63,10 +63,11 @@ | ||
| 63 | 63 | || strncmp(zUrl, "ssh://", 6)==0 |
| 64 | 64 | ){ |
| 65 | 65 | int iStart; |
| 66 | 66 | char *zLogin; |
| 67 | 67 | char *zExe; |
| 68 | + char cQuerySep = '?'; | |
| 68 | 69 | |
| 69 | 70 | g.urlIsFile = 0; |
| 70 | 71 | if( zUrl[4]=='s' ){ |
| 71 | 72 | g.urlIsHttps = 1; |
| 72 | 73 | g.urlProtocol = "https"; |
| @@ -75,10 +76,11 @@ | ||
| 75 | 76 | }else if( zUrl[0]=='s' ){ |
| 76 | 77 | g.urlIsSsh = 1; |
| 77 | 78 | g.urlProtocol = "ssh"; |
| 78 | 79 | g.urlDfltPort = 22; |
| 79 | 80 | g.urlFossil = "fossil"; |
| 81 | + g.urlShell = 0; | |
| 80 | 82 | iStart = 6; |
| 81 | 83 | }else{ |
| 82 | 84 | g.urlIsHttps = 0; |
| 83 | 85 | g.urlProtocol = "http"; |
| 84 | 86 | g.urlDfltPort = 80; |
| @@ -144,11 +146,18 @@ | ||
| 144 | 146 | i++; |
| 145 | 147 | } |
| 146 | 148 | if( fossil_strcmp(zName,"fossil")==0 ){ |
| 147 | 149 | g.urlFossil = zValue; |
| 148 | 150 | dehttpize(g.urlFossil); |
| 149 | - zExe = mprintf("?fossil=%T", g.urlFossil); | |
| 151 | + zExe = mprintf("%cfossil=%T", cQuerySep, g.urlFossil); | |
| 152 | + cQuerySep = '&'; | |
| 153 | + } | |
| 154 | + if( fossil_strcmp(zName,"shell")==0 ){ | |
| 155 | + g.urlShell = zValue; | |
| 156 | + dehttpize(g.urlShell); | |
| 157 | + zExe = mprintf("%cshell=%T", cQuerySep, g.urlFossil); | |
| 158 | + cQuerySep = '&'; | |
| 150 | 159 | } |
| 151 | 160 | } |
| 152 | 161 | |
| 153 | 162 | dehttpize(g.urlPath); |
| 154 | 163 | if( g.urlDfltPort==g.urlPort ){ |
| 155 | 164 |
| --- src/url.c | |
| +++ src/url.c | |
| @@ -63,10 +63,11 @@ | |
| 63 | || strncmp(zUrl, "ssh://", 6)==0 |
| 64 | ){ |
| 65 | int iStart; |
| 66 | char *zLogin; |
| 67 | char *zExe; |
| 68 | |
| 69 | g.urlIsFile = 0; |
| 70 | if( zUrl[4]=='s' ){ |
| 71 | g.urlIsHttps = 1; |
| 72 | g.urlProtocol = "https"; |
| @@ -75,10 +76,11 @@ | |
| 75 | }else if( zUrl[0]=='s' ){ |
| 76 | g.urlIsSsh = 1; |
| 77 | g.urlProtocol = "ssh"; |
| 78 | g.urlDfltPort = 22; |
| 79 | g.urlFossil = "fossil"; |
| 80 | iStart = 6; |
| 81 | }else{ |
| 82 | g.urlIsHttps = 0; |
| 83 | g.urlProtocol = "http"; |
| 84 | g.urlDfltPort = 80; |
| @@ -144,11 +146,18 @@ | |
| 144 | i++; |
| 145 | } |
| 146 | if( fossil_strcmp(zName,"fossil")==0 ){ |
| 147 | g.urlFossil = zValue; |
| 148 | dehttpize(g.urlFossil); |
| 149 | zExe = mprintf("?fossil=%T", g.urlFossil); |
| 150 | } |
| 151 | } |
| 152 | |
| 153 | dehttpize(g.urlPath); |
| 154 | if( g.urlDfltPort==g.urlPort ){ |
| 155 |
| --- src/url.c | |
| +++ src/url.c | |
| @@ -63,10 +63,11 @@ | |
| 63 | || strncmp(zUrl, "ssh://", 6)==0 |
| 64 | ){ |
| 65 | int iStart; |
| 66 | char *zLogin; |
| 67 | char *zExe; |
| 68 | char cQuerySep = '?'; |
| 69 | |
| 70 | g.urlIsFile = 0; |
| 71 | if( zUrl[4]=='s' ){ |
| 72 | g.urlIsHttps = 1; |
| 73 | g.urlProtocol = "https"; |
| @@ -75,10 +76,11 @@ | |
| 76 | }else if( zUrl[0]=='s' ){ |
| 77 | g.urlIsSsh = 1; |
| 78 | g.urlProtocol = "ssh"; |
| 79 | g.urlDfltPort = 22; |
| 80 | g.urlFossil = "fossil"; |
| 81 | g.urlShell = 0; |
| 82 | iStart = 6; |
| 83 | }else{ |
| 84 | g.urlIsHttps = 0; |
| 85 | g.urlProtocol = "http"; |
| 86 | g.urlDfltPort = 80; |
| @@ -144,11 +146,18 @@ | |
| 146 | i++; |
| 147 | } |
| 148 | if( fossil_strcmp(zName,"fossil")==0 ){ |
| 149 | g.urlFossil = zValue; |
| 150 | dehttpize(g.urlFossil); |
| 151 | zExe = mprintf("%cfossil=%T", cQuerySep, g.urlFossil); |
| 152 | cQuerySep = '&'; |
| 153 | } |
| 154 | if( fossil_strcmp(zName,"shell")==0 ){ |
| 155 | g.urlShell = zValue; |
| 156 | dehttpize(g.urlShell); |
| 157 | zExe = mprintf("%cshell=%T", cQuerySep, g.urlFossil); |
| 158 | cQuerySep = '&'; |
| 159 | } |
| 160 | } |
| 161 | |
| 162 | dehttpize(g.urlPath); |
| 163 | if( g.urlDfltPort==g.urlPort ){ |
| 164 |