Fossil

Check-in [dcc48662f8]
Login

Check-in [dcc48662f8]

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

Overview
Comment:Better error messages when trying to run "fossil ui" with an invalid or unaccessible repository.
Downloads: Tarball | ZIP archive
Timelines: family | ancestors | descendants | both | trunk
Files: files | file ages | folders
SHA1: dcc48662f838417842f182972517e785e2f3d444
User & Date: drh 2008-06-08 15:45:36.000
Context
2008-06-08
16:19
Bug fix in wiki rendering. Avoid terminating the output when an an unrecognized markup attribute appears inside <verbatim>. ... (check-in: 71104b898d user: drh tags: trunk)
15:45
Better error messages when trying to run "fossil ui" with an invalid or unaccessible repository. ... (check-in: dcc48662f8 user: drh tags: trunk)
15:10
Fix a C++-ism in report.c. ... (check-in: 9e2d2676a4 user: drh tags: trunk)
Changes
Unified Diff Ignore Whitespace Patch
Changes to src/cgi.c.
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
/*
** Additional information used to form the HTTP reply
*/
static char *zContentType = "text/html";     /* Content type of the reply */
static char *zReplyStatus = "OK";            /* Reply status description */
static int iReplyStatus = 200;               /* Reply status code */
static Blob extraHeader = BLOB_INITIALIZER;  /* Extra header text */
static int fullHttpReply = 0;      /* True for a full-blown HTTP header */

/*
** Set the reply content type
*/
void cgi_set_content_type(const char *zType){
  zContentType = mprintf("%s", zType);
}







<







151
152
153
154
155
156
157

158
159
160
161
162
163
164
/*
** Additional information used to form the HTTP reply
*/
static char *zContentType = "text/html";     /* Content type of the reply */
static char *zReplyStatus = "OK";            /* Reply status description */
static int iReplyStatus = 200;               /* Reply status code */
static Blob extraHeader = BLOB_INITIALIZER;  /* Extra header text */


/*
** Set the reply content type
*/
void cgi_set_content_type(const char *zType){
  zContentType = mprintf("%s", zType);
}
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
    ** body (code 200).
    */
    iReplyStatus = 304;
    zReplyStatus = "Not Modified";
  }
#endif

  if( fullHttpReply ){
    fprintf(g.httpOut, "HTTP/1.0 %d %s\r\n", iReplyStatus, zReplyStatus);
    fprintf(g.httpOut, "Date: %s\r\n", cgi_rfc822_datestamp(time(0)));
    fprintf(g.httpOut, "Connection: close\r\n");
  }else{
    fprintf(g.httpOut, "Status: %d %s\r\n", iReplyStatus, zReplyStatus);
  }








|







282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
    ** body (code 200).
    */
    iReplyStatus = 304;
    zReplyStatus = "Not Modified";
  }
#endif

  if( g.fullHttpReply ){
    fprintf(g.httpOut, "HTTP/1.0 %d %s\r\n", iReplyStatus, zReplyStatus);
    fprintf(g.httpOut, "Date: %s\r\n", cgi_rfc822_datestamp(time(0)));
    fprintf(g.httpOut, "Connection: close\r\n");
  }else{
    fprintf(g.httpOut, "Status: %d %s\r\n", iReplyStatus, zReplyStatus);
  }

1089
1090
1091
1092
1093
1094
1095
1096
1097
1098
1099
1100
1101
1102
1103
void cgi_handle_http_request(const char *zIpAddr){
  char *z, *zToken;
  int i;
  struct sockaddr_in remoteName;
  size_t size = sizeof(struct sockaddr_in);
  char zLine[2000];     /* A single line of input. */

  fullHttpReply = 1;
  if( fgets(zLine, sizeof(zLine),g.httpIn)==0 ){
    malformed_request();
  }
  zToken = extract_token(zLine, &z);
  if( zToken==0 ){
    malformed_request();
  }







|







1088
1089
1090
1091
1092
1093
1094
1095
1096
1097
1098
1099
1100
1101
1102
void cgi_handle_http_request(const char *zIpAddr){
  char *z, *zToken;
  int i;
  struct sockaddr_in remoteName;
  size_t size = sizeof(struct sockaddr_in);
  char zLine[2000];     /* A single line of input. */

  g.fullHttpReply = 1;
  if( fgets(zLine, sizeof(zLine),g.httpIn)==0 ){
    malformed_request();
  }
  zToken = extract_token(zLine, &z);
  if( zToken==0 ){
    malformed_request();
  }
Changes to src/main.c.
69
70
71
72
73
74
75

76
77
78
79
80
81
82
  char *zBaseURL;         /* Full text of the URL being served */
  char *zTop;             /* Parent directory of zPath */
  const char *zContentType;  /* The content type of the input HTTP request */
  int iErrPriority;       /* Priority of current error message */
  char *zErrMsg;          /* Text of an error message */
  Blob cgiIn;             /* Input to an xfer www method */
  int cgiPanic;           /* Write error messages to CGI */

  Th_Interp *interp;      /* The TH1 interpreter */
  FILE *httpIn;           /* Accept HTTP input from here */
  FILE *httpOut;          /* Send HTTP output here */
  int xlinkClusterOnly;   /* Set when cloning.  Only process clusters */

  int *aCommitFile;       /* Array of files to be committed */








>







69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
  char *zBaseURL;         /* Full text of the URL being served */
  char *zTop;             /* Parent directory of zPath */
  const char *zContentType;  /* The content type of the input HTTP request */
  int iErrPriority;       /* Priority of current error message */
  char *zErrMsg;          /* Text of an error message */
  Blob cgiIn;             /* Input to an xfer www method */
  int cgiPanic;           /* Write error messages to CGI */
  int fullHttpReply;      /* True for full HTTP reply.  False for CGI reply */
  Th_Interp *interp;      /* The TH1 interpreter */
  FILE *httpIn;           /* Accept HTTP input from here */
  FILE *httpOut;          /* Send HTTP output here */
  int xlinkClusterOnly;   /* Set when cloning.  Only process clusters */

  int *aCommitFile;       /* Array of files to be committed */

242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
  static int once = 1;
  va_start(ap, zFormat);
  z = vmprintf(zFormat, ap);
  va_end(ap);
  if( g.cgiPanic && once ){
    once = 0;
    cgi_printf("<p><font color=\"red\">%h</font></p>", z);
    style_footer();
    cgi_reply();
  }else{
    fprintf(stderr, "%s: %s\n", g.argv[0], z);
  }
  db_force_rollback();
  exit(1);
}
void fossil_fatal(const char *zFormat, ...){
  char *z;
  va_list ap;
  va_start(ap, zFormat);
  z = vmprintf(zFormat, ap);
  va_end(ap);
  if( g.cgiPanic ){
    g.cgiPanic = 0;
    cgi_printf("<p><font color=\"red\">%h</font></p>", z);
    style_footer();
    cgi_reply();
  }else{
    fprintf(stderr, "%s: %s\n", g.argv[0], z);
  }
  db_force_rollback();
  exit(1);
}







<
















<







243
244
245
246
247
248
249

250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265

266
267
268
269
270
271
272
  static int once = 1;
  va_start(ap, zFormat);
  z = vmprintf(zFormat, ap);
  va_end(ap);
  if( g.cgiPanic && once ){
    once = 0;
    cgi_printf("<p><font color=\"red\">%h</font></p>", z);

    cgi_reply();
  }else{
    fprintf(stderr, "%s: %s\n", g.argv[0], z);
  }
  db_force_rollback();
  exit(1);
}
void fossil_fatal(const char *zFormat, ...){
  char *z;
  va_list ap;
  va_start(ap, zFormat);
  z = vmprintf(zFormat, ap);
  va_end(ap);
  if( g.cgiPanic ){
    g.cgiPanic = 0;
    cgi_printf("<p><font color=\"red\">%h</font></p>", z);

    cgi_reply();
  }else{
    fprintf(stderr, "%s: %s\n", g.argv[0], z);
  }
  db_force_rollback();
  exit(1);
}
633
634
635
636
637
638
639
640
641
642
643
644
645
646
647
648
649
650
651
652




653


654
655
656
657
658
659
660
**
** Handle a single HTTP request appearing on stdin.  The resulting webpage
** is delivered on stdout.  This method is used to launch an HTTP request
** handler from inetd, for example.  The argument is the name of the 
** repository.
*/
void cmd_http(void){
  const char *zIpAddr = 0;
  if( g.argc!=2 && g.argc!=3 && g.argc!=6 ){
    cgi_panic("no repository specified");
  }
  g.cgiPanic = 1;
  g.httpIn = stdin;
  g.httpOut = stdout;
  if( g.argc>=3 ){
    db_open_repository(g.argv[2]);
    if( g.argc==6 ){
      g.httpIn = fopen(g.argv[3], "rb");
      g.httpOut = fopen(g.argv[4], "wb");
      zIpAddr = g.argv[5];




    }


  }else{
    db_must_be_within_tree();
  }
  cgi_handle_http_request(zIpAddr);
  process_one_web_page();
}








|




|
<
<
<
|
|
|
|
>
>
>
>
|
>
>







632
633
634
635
636
637
638
639
640
641
642
643
644



645
646
647
648
649
650
651
652
653
654
655
656
657
658
659
660
661
662
**
** Handle a single HTTP request appearing on stdin.  The resulting webpage
** is delivered on stdout.  This method is used to launch an HTTP request
** handler from inetd, for example.  The argument is the name of the 
** repository.
*/
void cmd_http(void){
  const char *zIpAddr;
  if( g.argc!=2 && g.argc!=3 && g.argc!=6 ){
    cgi_panic("no repository specified");
  }
  g.cgiPanic = 1;
  g.fullHttpReply = 1;



  if( g.argc==6 ){
    g.httpIn = fopen(g.argv[3], "rb");
    g.httpOut = fopen(g.argv[4], "wb");
    zIpAddr = g.argv[5];
  }else{
    g.httpIn = stdin;
    g.httpOut = stdout;
    zIpAddr = 0;
  }
  if( g.argc>=3 ){
    db_open_repository(g.argv[2]);
  }else{
    db_must_be_within_tree();
  }
  cgi_handle_http_request(zIpAddr);
  process_one_web_page();
}

694
695
696
697
698
699
700
701

702

703
704
705
706
707
708
709
    iPort = atoi(zPort);
  }else{
    iPort = 8080;
  }
  if( g.argc!=2 && g.argc!=3 ) usage("?REPOSITORY?");
  if( g.argc==2 ){
    db_must_be_within_tree();
    db_close();

  }

#ifndef __MINGW32__
  /* Unix implementation */
  if( g.argv[1][0]=='u' ){
#if !defined(__DARWIN__) && !defined(__APPLE__)
    zBrowser = db_get("web-browser", "firefox");
#else
    zBrowser = db_get("web-browser", "open");







|
>

>







696
697
698
699
700
701
702
703
704
705
706
707
708
709
710
711
712
713
    iPort = atoi(zPort);
  }else{
    iPort = 8080;
  }
  if( g.argc!=2 && g.argc!=3 ) usage("?REPOSITORY?");
  if( g.argc==2 ){
    db_must_be_within_tree();
  }else{
    db_open_repository(g.argv[2]);
  }
  db_close();
#ifndef __MINGW32__
  /* Unix implementation */
  if( g.argv[1][0]=='u' ){
#if !defined(__DARWIN__) && !defined(__APPLE__)
    zBrowser = db_get("web-browser", "firefox");
#else
    zBrowser = db_get("web-browser", "open");
Changes to src/style.c.
38
39
40
41
42
43
44






45
46
47
48
49
50
51
static struct Submenu {
  const char *zLabel;
  const char *zTitle;
  const char *zLink;
} aSubmenu[30];
static int nSubmenu = 0;







/*
** Add a new element to the submenu
*/
void style_submenu_element(
  const char *zLabel,
  const char *zTitle,
  const char *zLink,







>
>
>
>
>
>







38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
static struct Submenu {
  const char *zLabel;
  const char *zTitle;
  const char *zLink;
} aSubmenu[30];
static int nSubmenu = 0;

/*
** Remember that the header has been generated.  The footer is omitted
** if an error occurs before the header.
*/
static int headerHasBeenGenerated = 0;

/*
** Add a new element to the submenu
*/
void style_submenu_element(
  const char *zLabel,
  const char *zTitle,
  const char *zLink,
96
97
98
99
100
101
102

103
104
105
106
107
108
109


110
111
112
113
114
115
116
  if( g.zLogin ){
    Th_Store("login", g.zLogin);
  }
  Th_Render(zHeader);
  Th_Unstore("title");   /* Avoid collisions with ticket field names */
  cgi_destination(CGI_BODY);
  g.cgiPanic = 1;

}

/*
** Draw the footer at the bottom of the page.
*/
void style_footer(void){
  const char *zFooter;


  
  /* Go back and put the submenu at the top of the page.  We delay the
  ** creation of the submenu until the end so that we can add elements
  ** to the submenu while generating page text.
  */
  if( nSubmenu>0 ){
    int i;







>







>
>







102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
  if( g.zLogin ){
    Th_Store("login", g.zLogin);
  }
  Th_Render(zHeader);
  Th_Unstore("title");   /* Avoid collisions with ticket field names */
  cgi_destination(CGI_BODY);
  g.cgiPanic = 1;
  headerHasBeenGenerated = 1;
}

/*
** Draw the footer at the bottom of the page.
*/
void style_footer(void){
  const char *zFooter;

  if( !headerHasBeenGenerated ) return;
  
  /* Go back and put the submenu at the top of the page.  We delay the
  ** creation of the submenu until the end so that we can add elements
  ** to the submenu while generating page text.
  */
  if( nSubmenu>0 ){
    int i;