Many hyperlinks are disabled.
Use anonymous login
to enable hyperlinks.
Overview
| Comment: | Add the %w and %W formatting options for internal printf usage. Use these formatting characters to render wiki. Fix additional problems of unterminated wiki on webpage rendering by using %w. (There are probably more problems yet to be discovered and fixed.) |
|---|---|
| Downloads: | Tarball | ZIP archive |
| Timelines: | family | ancestors | descendants | both | trunk |
| Files: | files | file ages | folders |
| SHA1: |
285929373757b9813748fd31744b4379 |
| User & Date: | drh 2007-11-22 22:55:05.000 |
Context
|
2007-11-23
| ||
| 12:49 | Remove obsolete file containing sample ticket configuration script. check-in: 6311ce2ec1 user: drh tags: trunk | |
|
2007-11-22
| ||
| 22:55 | Add the %w and %W formatting options for internal printf usage. Use these formatting characters to render wiki. Fix additional problems of unterminated wiki on webpage rendering by using %w. (There are probably more problems yet to be discovered and fixed.) check-in: 2859293737 user: drh tags: trunk | |
| 22:14 | Make sure HTML tags in wiki are terminated in the diff screen too. check-in: d6ad7aa034 user: drh tags: trunk | |
Changes
Changes to src/blob.c.
| ︙ | ︙ | |||
537 538 539 540 541 542 543 |
*/
int blob_tokenize(Blob *pIn, Blob *aToken, int nToken){
int i;
for(i=0; i<nToken && blob_token(pIn, &aToken[i]); i++){}
return i;
}
| < < < < < < < < < < < | | | 537 538 539 540 541 542 543 544 545 546 547 548 549 550 551 552 553 554 555 556 557 558 559 560 561 |
*/
int blob_tokenize(Blob *pIn, Blob *aToken, int nToken){
int i;
for(i=0; i<nToken && blob_token(pIn, &aToken[i]); i++){}
return i;
}
/*
** Do printf-style string rendering and append the results to a blob.
*/
void blob_appendf(Blob *pBlob, const char *zFormat, ...){
va_list ap;
va_start(ap, zFormat);
vxprintf(pBlob, zFormat, ap);
va_end(ap);
}
void blob_vappendf(Blob *pBlob, const char *zFormat, va_list ap){
vxprintf(pBlob, zFormat, ap);
}
/*
** Initalize a blob to the data on an input channel. Return
** the number of bytes read into the blob. Any prior content
** of the blob is discarded, not freed.
*/
|
| ︙ | ︙ |
Changes to src/cgi.c.
| ︙ | ︙ | |||
918 919 920 921 922 923 924 |
strcmp(zVal, zD) ? "" : " selected"
);
}
}
cgi_printf("%*s</select>\n", in, "");
}
| < < < < < < < < < < | | | 918 919 920 921 922 923 924 925 926 927 928 929 930 931 932 933 934 935 936 937 938 939 940 941 942 943 944 945 946 947 948 |
strcmp(zVal, zD) ? "" : " selected"
);
}
}
cgi_printf("%*s</select>\n", in, "");
}
/*
** This routine works like "printf" except that it has the
** extra formatting capabilities such as %h and %t.
*/
void cgi_printf(const char *zFormat, ...){
va_list ap;
va_start(ap,zFormat);
vxprintf(&cgiContent,zFormat,ap);
va_end(ap);
}
/*
** This routine works like "vprintf" except that it has the
** extra formatting capabilities such as %h and %t.
*/
void cgi_vprintf(const char *zFormat, va_list ap){
vxprintf(&cgiContent,zFormat,ap);
}
/*
** Send a reply indicating that the HTTP request was malformed
*/
static void malformed_request(void){
|
| ︙ | ︙ | |||
972 973 974 975 976 977 978 |
cgi_reset_content();
cgi_set_status(500, "Internal Server Error");
cgi_printf(
"<html><body><h1>Internal Server Error</h1>\n"
"<plaintext>"
);
va_start(ap, zFormat);
| | | 962 963 964 965 966 967 968 969 970 971 972 973 974 975 976 |
cgi_reset_content();
cgi_set_status(500, "Internal Server Error");
cgi_printf(
"<html><body><h1>Internal Server Error</h1>\n"
"<plaintext>"
);
va_start(ap, zFormat);
vxprintf(&cgiContent,zFormat,ap);
va_end(ap);
cgi_reply();
exit(1);
}
/*
** Remove the first space-delimited token from a string and return
|
| ︙ | ︙ |
Changes to src/info.c.
| ︙ | ︙ | |||
137 138 139 140 141 142 143 |
if( zTitle ){
@ <div class="section-title">%s(zTitle)</div>
}
@ <ul>
}
@ <li>
hyperlink_to_uuid(zUuid);
| | | 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 |
if( zTitle ){
@ <div class="section-title">%s(zTitle)</div>
}
@ <ul>
}
@ <li>
hyperlink_to_uuid(zUuid);
@ %w(zCom) (by %s(zUser) on %s(zDate))
if( depth ){
n = showDescendents(cid, depth-1, 0);
}else{
n = db_int(0, "SELECT 1 FROM plink WHERE pid=%d", cid);
}
if( n==0 ){
db_multi_exec("DELETE FROM leaves WHERE rid=%d", cid);
|
| ︙ | ︙ | |||
188 189 190 191 192 193 194 |
if( zTitle ){
@ <div class="section-title">%s(zTitle)</div>
}
@ <ul>
}
@ <li>
hyperlink_to_uuid(zUuid);
| | | 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 |
if( zTitle ){
@ <div class="section-title">%s(zTitle)</div>
}
@ <ul>
}
@ <li>
hyperlink_to_uuid(zUuid);
@ %w(zCom) (by %s(zUser) on %s(zDate))
if( depth ){
showAncestors(cid, depth-1, 0);
}
}
db_finalize(&q);
if( cnt ){
@ </ul>
|
| ︙ | ︙ | |||
227 228 229 230 231 232 233 |
cnt++;
if( cnt==1 ){
@ <div class="section-title">Leaves</div>
@ <ul>
}
@ <li>
hyperlink_to_uuid(zUuid);
| | | 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 |
cnt++;
if( cnt==1 ){
@ <div class="section-title">Leaves</div>
@ <ul>
}
@ <li>
hyperlink_to_uuid(zUuid);
@ %w(zCom) (by %s(zUser) on %s(zDate))
}
db_finalize(&q);
if( cnt ){
@ </ul>
}
}
|
| ︙ | ︙ | |||
314 315 316 317 318 319 320 |
"SELECT uuid, datetime(mtime, 'localtime'), user, comment"
" FROM blob, event"
" WHERE blob.rid=%d"
" AND event.objid=%d",
rid, rid
);
if( db_step(&q)==SQLITE_ROW ){
| < | | < < | 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 |
"SELECT uuid, datetime(mtime, 'localtime'), user, comment"
" FROM blob, event"
" WHERE blob.rid=%d"
" AND event.objid=%d",
rid, rid
);
if( db_step(&q)==SQLITE_ROW ){
const char *zUuid = db_column_text(&q, 0);
char *zTitle = mprintf("Version: [%.10s]", zUuid);
style_header(zTitle);
free(zTitle);
/*@ <h2>Version %s(zUuid)</h2>*/
@ <div class="section-title">Overview</div>
@ <p><table class="label-value">
@ <tr><th>Version:</th><td>%s(zUuid)</td></tr>
@ <tr><th>Date:</th><td>%s(db_column_text(&q, 1))</td></tr>
if( g.okSetup ){
@ <tr><th>Record ID:</th><td>%d(rid)</td></tr>
}
@ <tr><th>Original User:</th><td>%h(db_column_text(&q, 2))</td></tr>
@ <tr><th>Original Comment:</th><td>%w(db_column_text(&q,3))</td></tr>
@ </td></tr>
@ <tr><th>Commands:</th>
@ <td>
@ <a href="%s(g.zBaseURL)/vdiff/%d(rid)">diff</a>
@ | <a href="%s(g.zBaseURL)/zip/%s(zUuid).zip">ZIP archive</a>
@ | <a href="%s(g.zBaseURL)/fview/%d(rid)">manifest</a>
@ </td>
|
| ︙ | ︙ | |||
600 601 602 603 604 605 606 607 608 |
" AND mlink.fid=%d",
rid
);
while( db_step(&q)==SQLITE_ROW ){
const char *zName = db_column_text(&q, 0);
const char *zDate = db_column_text(&q, 1);
const char *zFuuid = db_column_text(&q, 2);
const char *zUser = db_column_text(&q, 4);
const char *zVers = db_column_text(&q, 5);
| > < < < | < < | 597 598 599 600 601 602 603 604 605 606 607 608 609 610 611 612 613 614 615 616 617 |
" AND mlink.fid=%d",
rid
);
while( db_step(&q)==SQLITE_ROW ){
const char *zName = db_column_text(&q, 0);
const char *zDate = db_column_text(&q, 1);
const char *zFuuid = db_column_text(&q, 2);
const char *zCom = db_column_text(&q, 3);
const char *zUser = db_column_text(&q, 4);
const char *zVers = db_column_text(&q, 5);
@ File <a href="%s(g.zBaseURL)/finfo?name=%T(zName)">%h(zName)</a>
@ uuid %s(zFuuid) part of check-in
hyperlink_to_uuid(zVers);
@ %w(zCom) by %h(zUser) on %s(zDate)
cnt++;
}
db_finalize(&q);
db_prepare(&q,
"SELECT substr(tagname, 6, 10000), datetime(event.mtime),"
" coalesce(event.euser, event.user), uuid"
" FROM tagxref, tag, event, blob"
|
| ︙ | ︙ | |||
649 650 651 652 653 654 655 |
" AND blob.rid=%d",
rid, rid
);
while( db_step(&q)==SQLITE_ROW ){
const char *zDate = db_column_text(&q, 0);
const char *zUuid = db_column_text(&q, 3);
const char *zUser = db_column_text(&q, 1);
| | < < | < < | 642 643 644 645 646 647 648 649 650 651 652 653 654 655 656 657 658 659 |
" AND blob.rid=%d",
rid, rid
);
while( db_step(&q)==SQLITE_ROW ){
const char *zDate = db_column_text(&q, 0);
const char *zUuid = db_column_text(&q, 3);
const char *zUser = db_column_text(&q, 1);
const char *zCom = db_column_text(&q, 2);
@ Manifest of version
hyperlink_to_uuid(zUuid);
@ %w(zCom) by %h(zUser) on %s(zDate)
cnt++;
}
db_finalize(&q);
}
if( cnt==0 ){
char *zUuid = db_text(0, "SELECT uuid FROM blob WHERE rid=%d", rid);
@ Control file %s(zUuid).
|
| ︙ | ︙ |
Changes to src/printf.c.
| ︙ | ︙ | |||
48 49 50 51 52 53 54 55 56 57 58 59 60 61 |
NULL pointers replaced by SQL NULL. %Q */
#define etPOINTER 15 /* The %p conversion */
#define etHTMLIZE 16 /* Make text safe for HTML */
#define etHTTPIZE 17 /* Make text safe for HTTP. "/" encoded as %2f */
#define etURLIZE 18 /* Make text safe for HTTP. "/" not encoded */
#define etFOSSILIZE 19 /* The fossil header encoding format. */
#define etPATH 20 /* Path type */
/*
** An "etByte" is an 8-bit unsigned value.
*/
typedef unsigned char etByte;
| > > | 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 |
NULL pointers replaced by SQL NULL. %Q */
#define etPOINTER 15 /* The %p conversion */
#define etHTMLIZE 16 /* Make text safe for HTML */
#define etHTTPIZE 17 /* Make text safe for HTTP. "/" encoded as %2f */
#define etURLIZE 18 /* Make text safe for HTTP. "/" not encoded */
#define etFOSSILIZE 19 /* The fossil header encoding format. */
#define etPATH 20 /* Path type */
#define etWIKISTR 21 /* Wiki text rendered from a char* */
#define etWIKIBLOB 22 /* Wiki text rendered from a Blob* */
/*
** An "etByte" is an 8-bit unsigned value.
*/
typedef unsigned char etByte;
|
| ︙ | ︙ | |||
91 92 93 94 95 96 97 98 99 100 101 102 103 104 |
{ 's', 0, 4, etSTRING, 0, 0 },
{ 'g', 0, 1, etGENERIC, 30, 0 },
{ 'z', 0, 6, etDYNSTRING, 0, 0 },
{ 'q', 0, 4, etSQLESCAPE, 0, 0 },
{ 'Q', 0, 4, etSQLESCAPE2, 0, 0 },
{ 'b', 0, 2, etBLOB, 0, 0 },
{ 'B', 0, 2, etBLOBSQL, 0, 0 },
{ 'h', 0, 4, etHTMLIZE, 0, 0 },
{ 't', 0, 4, etHTTPIZE, 0, 0 }, /* "/" -> "%2F" */
{ 'T', 0, 4, etURLIZE, 0, 0 }, /* "/" unchanged */
{ 'F', 0, 4, etFOSSILIZE, 0, 0 },
{ 'c', 0, 0, etCHARX, 0, 0 },
{ 'o', 8, 0, etRADIX, 0, 2 },
{ 'u', 10, 0, etRADIX, 0, 0 },
| > > | 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 |
{ 's', 0, 4, etSTRING, 0, 0 },
{ 'g', 0, 1, etGENERIC, 30, 0 },
{ 'z', 0, 6, etDYNSTRING, 0, 0 },
{ 'q', 0, 4, etSQLESCAPE, 0, 0 },
{ 'Q', 0, 4, etSQLESCAPE2, 0, 0 },
{ 'b', 0, 2, etBLOB, 0, 0 },
{ 'B', 0, 2, etBLOBSQL, 0, 0 },
{ 'w', 0, 2, etWIKISTR, 0, 0 },
{ 'W', 0, 2, etWIKIBLOB, 0, 0 },
{ 'h', 0, 4, etHTMLIZE, 0, 0 },
{ 't', 0, 4, etHTTPIZE, 0, 0 }, /* "/" -> "%2F" */
{ 'T', 0, 4, etURLIZE, 0, 0 }, /* "/" unchanged */
{ 'F', 0, 4, etFOSSILIZE, 0, 0 },
{ 'c', 0, 0, etCHARX, 0, 0 },
{ 'o', 8, 0, etRADIX, 0, 2 },
{ 'u', 10, 0, etRADIX, 0, 0 },
|
| ︙ | ︙ | |||
169 170 171 172 173 174 175 | ** the function "func". Returns -1 on a error. ** ** Note that the order in which automatic variables are declared below ** seems to make a big difference in determining how fast this beast ** will run. */ int vxprintf( | < | | 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 |
** the function "func". Returns -1 on a error.
**
** Note that the order in which automatic variables are declared below
** seems to make a big difference in determining how fast this beast
** will run.
*/
int vxprintf(
Blob *pBlob, /* Append output to this blob */
const char *fmt, /* Format string */
va_list ap /* arguments */
){
int c; /* Next character in the format string */
char *bufpt; /* Pointer to the conversion buffer */
int precision; /* Precision of the current field */
int length; /* Length of the field */
|
| ︙ | ︙ | |||
208 209 210 211 212 213 214 | int exp, e2; /* exponent of real numbers */ double rounder; /* Used for rounding floating point values */ etByte flag_dp; /* True if decimal point should be shown */ etByte flag_rtz; /* True if trailing zeros should be removed */ etByte flag_exp; /* True to force display of the exponent */ int nsd; /* Number of significant digits returned */ | < | | | 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 |
int exp, e2; /* exponent of real numbers */
double rounder; /* Used for rounding floating point values */
etByte flag_dp; /* True if decimal point should be shown */
etByte flag_rtz; /* True if trailing zeros should be removed */
etByte flag_exp; /* True to force display of the exponent */
int nsd; /* Number of significant digits returned */
count = length = 0;
bufpt = 0;
for(; (c=(*fmt))!=0; ++fmt){
if( c!='%' ){
int amt;
bufpt = (char *)fmt;
amt = 1;
while( (c=(*++fmt))!='%' && c!=0 ) amt++;
blob_append(pBlob,bufpt,amt);
count += amt;
if( c==0 ) break;
}
if( (c=(*++fmt))==0 ){
errorflag = 1;
blob_append(pBlob,"%",1);
count++;
break;
}
/* Find out what flags are present */
flag_leftjustify = flag_plussign = flag_blanksign =
flag_alternateform = flag_altform2 = flag_zeropad = 0;
done = 0;
|
| ︙ | ︙ | |||
656 657 658 659 660 661 662 663 664 665 666 667 668 |
case etFOSSILIZE: {
char *zMem = va_arg(ap,char*);
if( zMem==0 ) zMem = "";
zExtra = bufpt = fossilize(zMem, -1);
length = strlen(bufpt);
if( precision>=0 && precision<length ) length = precision;
break;
}
case etERROR:
buf[0] = '%';
buf[1] = c;
errorflag = 0;
idx = 1+(c!=0);
| > > > > > > > > > > > > > > > | | | | | | | 658 659 660 661 662 663 664 665 666 667 668 669 670 671 672 673 674 675 676 677 678 679 680 681 682 683 684 685 686 687 688 689 690 691 692 693 694 695 696 697 698 699 700 701 702 703 704 705 706 707 708 709 710 711 712 713 714 715 716 717 718 719 720 721 722 723 724 725 726 727 728 |
case etFOSSILIZE: {
char *zMem = va_arg(ap,char*);
if( zMem==0 ) zMem = "";
zExtra = bufpt = fossilize(zMem, -1);
length = strlen(bufpt);
if( precision>=0 && precision<length ) length = precision;
break;
}
case etWIKISTR: {
char *zWiki = va_arg(ap, char*);
Blob wiki;
blob_init(&wiki, zWiki, -1);
wiki_convert(&wiki, pBlob, WIKI_INLINE);
blob_reset(&wiki);
length = width = 0;
break;
}
case etWIKIBLOB: {
Blob *pWiki = va_arg(ap, Blob*);
wiki_convert(pWiki, pBlob, WIKI_INLINE);
length = width = 0;
break;
}
case etERROR:
buf[0] = '%';
buf[1] = c;
errorflag = 0;
idx = 1+(c!=0);
blob_append(pBlob,"%",idx);
count += idx;
if( c==0 ) fmt--;
break;
}/* End switch over the format type */
/*
** The text of the conversion is pointed to by "bufpt" and is
** "length" characters long. The field width is "width". Do
** the output.
*/
if( !flag_leftjustify ){
register int nspace;
nspace = width-length;
if( nspace>0 ){
count += nspace;
while( nspace>=etSPACESIZE ){
blob_append(pBlob,spaces,etSPACESIZE);
nspace -= etSPACESIZE;
}
if( nspace>0 ) blob_append(pBlob,spaces,nspace);
}
}
if( length>0 ){
blob_append(pBlob,bufpt,length);
count += length;
}
if( flag_leftjustify ){
register int nspace;
nspace = width-length;
if( nspace>0 ){
count += nspace;
while( nspace>=etSPACESIZE ){
blob_append(pBlob,spaces,etSPACESIZE);
nspace -= etSPACESIZE;
}
if( nspace>0 ) blob_append(pBlob,spaces,nspace);
}
}
if( zExtra ){
free(zExtra);
}
}/* End for loop over the format string */
return errorflag ? -1 : count;
|
| ︙ | ︙ |