| | @@ -267,24 +267,40 @@ |
| 267 | 267 | ** message string. Call fossil_mbcs_free() to deallocate any memory used |
| 268 | 268 | ** to store the message string when done. |
| 269 | 269 | */ |
| 270 | 270 | static char *win32_get_last_errmsg(void){ |
| 271 | 271 | DWORD nMsg; |
| 272 | + DWORD nErr = GetLastError(); |
| 272 | 273 | LPTSTR tmp = NULL; |
| 273 | 274 | char *zMsg = NULL; |
| 274 | 275 | |
| 276 | + /* Try first to get the error text in english. */ |
| 275 | 277 | nMsg = FormatMessage( |
| 276 | 278 | FORMAT_MESSAGE_ALLOCATE_BUFFER | |
| 277 | 279 | FORMAT_MESSAGE_FROM_SYSTEM | |
| 278 | 280 | FORMAT_MESSAGE_IGNORE_INSERTS, |
| 279 | 281 | NULL, |
| 280 | | - GetLastError(), |
| 282 | + nErr, |
| 281 | 283 | MAKELANGID(LANG_ENGLISH, SUBLANG_ENGLISH_US), |
| 282 | 284 | (LPTSTR) &tmp, |
| 283 | 285 | 0, |
| 284 | 286 | NULL |
| 285 | 287 | ); |
| 288 | + if( !nMsg ){ |
| 289 | + /* No english, get what the system has available. */ |
| 290 | + nMsg = FormatMessage( |
| 291 | + FORMAT_MESSAGE_ALLOCATE_BUFFER | |
| 292 | + FORMAT_MESSAGE_FROM_SYSTEM | |
| 293 | + FORMAT_MESSAGE_IGNORE_INSERTS, |
| 294 | + NULL, |
| 295 | + nErr, |
| 296 | + 0, |
| 297 | + (LPTSTR) &tmp, |
| 298 | + 0, |
| 299 | + NULL |
| 300 | + ); |
| 301 | + } |
| 286 | 302 | if( nMsg ){ |
| 287 | 303 | zMsg = fossil_mbcs_to_utf8(tmp); |
| 288 | 304 | }else{ |
| 289 | 305 | fossil_fatal("unable to get system error message."); |
| 290 | 306 | } |
| | @@ -301,11 +317,11 @@ |
| 301 | 317 | static void win32_report_service_status( |
| 302 | 318 | DWORD dwCurrentState, /* The current state of the service */ |
| 303 | 319 | DWORD dwWin32ExitCode, /* The error code to report */ |
| 304 | 320 | DWORD dwWaitHint /* The estimated time for a pending operation */ |
| 305 | 321 | ){ |
| 306 | | - if( dwCurrentState==SERVICE_START_PENDING) { |
| 322 | + if( dwCurrentState==SERVICE_START_PENDING ){ |
| 307 | 323 | ssStatus.dwControlsAccepted = 0; |
| 308 | 324 | }else{ |
| 309 | 325 | ssStatus.dwControlsAccepted = SERVICE_ACCEPT_STOP; |
| 310 | 326 | } |
| 311 | 327 | ssStatus.dwCurrentState = dwCurrentState; |
| | @@ -477,11 +493,11 @@ |
| 477 | 493 | ** Password for the user account. |
| 478 | 494 | ** |
| 479 | 495 | ** The following options are more or less the same as for the "server" |
| 480 | 496 | ** command and influence the behaviour of the http server: |
| 481 | 497 | ** |
| 482 | | -** -p|--port TCPPORT |
| 498 | +** -P|--port TCPPORT |
| 483 | 499 | ** |
| 484 | 500 | ** Specifies the TCP port (default port is 8080) on which the |
| 485 | 501 | ** server should listen. |
| 486 | 502 | ** |
| 487 | 503 | ** -R|--repository REPOSITORY |
| | @@ -544,69 +560,62 @@ |
| 544 | 560 | if( g.argc<3 ){ |
| 545 | 561 | usage("create|delete|show|start|stop ..."); |
| 546 | 562 | } |
| 547 | 563 | zMethod = g.argv[2]; |
| 548 | 564 | n = strlen(zMethod); |
| 549 | | - if( g.argc==4 ){ |
| 550 | | - zSvcName = g.argv[3]; |
| 551 | | - } |
| 552 | 565 | |
| 553 | 566 | if( strncmp(zMethod, "create", n)==0 ){ |
| 554 | 567 | SC_HANDLE hScm; |
| 555 | 568 | SC_HANDLE hSvc; |
| 556 | 569 | SERVICE_DESCRIPTION |
| 557 | 570 | svcDescr = {"Fossil - Distributed Software Configuration Management"}; |
| 558 | 571 | char *zErrFmt = "unable to create service '%s': %s"; |
| 559 | 572 | DWORD dwStartType = SERVICE_DEMAND_START; |
| 560 | | - const char *zDisplay; |
| 561 | | - const char *zStart; |
| 562 | | - const char *zUsername; |
| 563 | | - const char *zPassword; |
| 564 | | - const char *zPort; |
| 565 | | - const char *zNotFound; |
| 566 | | - const char *zLocalAuth; |
| 567 | | - const char *zRepository; |
| 573 | + const char *zDisplay = find_option("display", "D", 1); |
| 574 | + const char *zStart = find_option("start", "S", 1); |
| 575 | + const char *zUsername = find_option("username", "U", 1); |
| 576 | + const char *zPassword = find_option("password", "W", 1); |
| 577 | + const char *zPort = find_option("port", "P", 1); |
| 578 | + const char *zNotFound = find_option("notfound", 0, 1); |
| 579 | + const char *zLocalAuth = find_option("localauth", 0, 0); |
| 580 | + const char *zRepository = find_option("repository", "R", 1); |
| 568 | 581 | Blob binPath; |
| 569 | 582 | |
| 583 | + verify_all_options(); |
| 584 | + if( g.argc==4 ){ |
| 585 | + zSvcName = g.argv[3]; |
| 586 | + }else if( g.argc>4 ){ |
| 587 | + fossil_fatal("to much arguments for create method."); |
| 588 | + } |
| 570 | 589 | /* Process service creation specific options. */ |
| 571 | | - zDisplay = find_option("display", "D", 1); |
| 572 | 590 | if( !zDisplay ){ |
| 573 | 591 | zDisplay = zSvcName; |
| 574 | 592 | } |
| 575 | | - zStart = find_option("start", "S", 1); |
| 576 | 593 | if( zStart ){ |
| 577 | 594 | if( strncmp(zStart, "auto", strlen(zStart))==0 ){ |
| 578 | 595 | dwStartType = SERVICE_AUTO_START; |
| 579 | | - }else if( strncmp(zStart, "manual", strlen(zStart))==0 ){ |
| 596 | + }else if( strncmp(zStart, "manual", strlen(zStart))==0 ){ |
| 580 | 597 | dwStartType = SERVICE_DEMAND_START; |
| 581 | 598 | }else{ |
| 582 | 599 | fossil_fatal(zErrFmt, zSvcName, |
| 583 | 600 | "specify 'auto' or 'manual' for the '-S|--start' option"); |
| 584 | 601 | } |
| 585 | 602 | } |
| 586 | | - zUsername = find_option("username", "U", 1); |
| 587 | | - zPassword = find_option("password", "W", 1); |
| 588 | 603 | /* Process options for Fossil running as server. */ |
| 589 | | - zPort = find_option("port", "P", 1); |
| 590 | 604 | if( zPort && (atoi(zPort)<=0) ){ |
| 591 | 605 | fossil_fatal(zErrFmt, zSvcName, |
| 592 | 606 | "port number must be in the range 1 - 65535."); |
| 593 | 607 | } |
| 594 | | - zNotFound = find_option("notfound", 0, 1); |
| 595 | | - zLocalAuth = find_option("localauth", 0, 0); |
| 596 | | - zRepository = find_option("repository", "R", 1); |
| 597 | 608 | if( !zRepository ){ |
| 598 | 609 | db_must_be_within_tree(); |
| 599 | 610 | }else if( file_isdir(zRepository)==1 ){ |
| 600 | 611 | g.zRepositoryName = mprintf("%s", zRepository); |
| 601 | 612 | file_simplify_name(g.zRepositoryName, -1, 0); |
| 602 | 613 | }else{ |
| 603 | 614 | db_open_repository(zRepository); |
| 604 | 615 | } |
| 605 | 616 | db_close(0); |
| 606 | | - verify_all_options(); |
| 607 | | - if( g.argc>4 ) fossil_fatal("to much arguments for create method."); |
| 608 | 617 | /* Build the fully-qualified path to the service binary file. */ |
| 609 | 618 | blob_zero(&binPath); |
| 610 | 619 | blob_appendf(&binPath, "\"%s\" server", fossil_nameofexe()); |
| 611 | 620 | if( zPort ) blob_appendf(&binPath, " --port %s", zPort); |
| 612 | 621 | if( zNotFound ) blob_appendf(&binPath, " --notfound \"%s\"", zNotFound); |
| | @@ -642,11 +651,15 @@ |
| 642 | 651 | SC_HANDLE hSvc; |
| 643 | 652 | SERVICE_STATUS sstat; |
| 644 | 653 | char *zErrFmt = "unable to delete service '%s': %s"; |
| 645 | 654 | |
| 646 | 655 | verify_all_options(); |
| 647 | | - if( g.argc>4 ) fossil_fatal("to much arguments for delete method."); |
| 656 | + if( g.argc==4 ){ |
| 657 | + zSvcName = g.argv[3]; |
| 658 | + }else if( g.argc>4 ){ |
| 659 | + fossil_fatal("to much arguments for delete method."); |
| 660 | + } |
| 648 | 661 | hScm = OpenSCManager(NULL, NULL, SC_MANAGER_ALL_ACCESS); |
| 649 | 662 | if( !hScm ) fossil_fatal(zErrFmt, zSvcName, win32_get_last_errmsg()); |
| 650 | 663 | hSvc = OpenService(hScm, fossil_utf8_to_mbcs(zSvcName), SERVICE_ALL_ACCESS); |
| 651 | 664 | if( !hSvc ) fossil_fatal(zErrFmt, zSvcName, win32_get_last_errmsg()); |
| 652 | 665 | QueryServiceStatus(hSvc, &sstat); |
| | @@ -706,11 +719,15 @@ |
| 706 | 719 | "Continue pending", "Pause pending", "Paused" |
| 707 | 720 | }; |
| 708 | 721 | const char *zSvcState = ""; |
| 709 | 722 | |
| 710 | 723 | verify_all_options(); |
| 711 | | - if( g.argc>4 ) fossil_fatal("to much arguments for show method."); |
| 724 | + if( g.argc==4 ){ |
| 725 | + zSvcName = g.argv[3]; |
| 726 | + }else if( g.argc>4 ){ |
| 727 | + fossil_fatal("to much arguments for show method."); |
| 728 | + } |
| 712 | 729 | hScm = OpenSCManager(NULL, NULL, GENERIC_READ); |
| 713 | 730 | if( !hScm ) fossil_fatal(zErrFmt, zSvcName, win32_get_last_errmsg()); |
| 714 | 731 | hSvc = OpenService(hScm, fossil_utf8_to_mbcs(zSvcName), GENERIC_READ); |
| 715 | 732 | if( !hSvc ) fossil_fatal(zErrFmt, zSvcName, win32_get_last_errmsg()); |
| 716 | 733 | /* Get the service configuration */ |
| | @@ -784,11 +801,15 @@ |
| 784 | 801 | SC_HANDLE hSvc; |
| 785 | 802 | SERVICE_STATUS sstat; |
| 786 | 803 | char *zErrFmt = "unable to start service '%s': %s"; |
| 787 | 804 | |
| 788 | 805 | verify_all_options(); |
| 789 | | - if( g.argc>4 ) fossil_fatal("to much arguments for start method."); |
| 806 | + if( g.argc==4 ){ |
| 807 | + zSvcName = g.argv[3]; |
| 808 | + }else if( g.argc>4 ){ |
| 809 | + fossil_fatal("to much arguments for start method."); |
| 810 | + } |
| 790 | 811 | hScm = OpenSCManager(NULL, NULL, SC_MANAGER_ALL_ACCESS); |
| 791 | 812 | if( !hScm ) fossil_fatal(zErrFmt, zSvcName, win32_get_last_errmsg()); |
| 792 | 813 | hSvc = OpenService(hScm, fossil_utf8_to_mbcs(zSvcName), SERVICE_ALL_ACCESS); |
| 793 | 814 | if( !hSvc ) fossil_fatal(zErrFmt, zSvcName, win32_get_last_errmsg()); |
| 794 | 815 | QueryServiceStatus(hSvc, &sstat); |
| | @@ -816,11 +837,15 @@ |
| 816 | 837 | SC_HANDLE hSvc; |
| 817 | 838 | SERVICE_STATUS sstat; |
| 818 | 839 | char *zErrFmt = "unable to stop service '%s': %s"; |
| 819 | 840 | |
| 820 | 841 | verify_all_options(); |
| 821 | | - if( g.argc>4 ) fossil_fatal("to much arguments for stop method."); |
| 842 | + if( g.argc==4 ){ |
| 843 | + zSvcName = g.argv[3]; |
| 844 | + }else if( g.argc>4 ){ |
| 845 | + fossil_fatal("to much arguments for stop method."); |
| 846 | + } |
| 822 | 847 | hScm = OpenSCManager(NULL, NULL, SC_MANAGER_ALL_ACCESS); |
| 823 | 848 | if( !hScm ) fossil_fatal(zErrFmt, zSvcName, win32_get_last_errmsg()); |
| 824 | 849 | hSvc = OpenService(hScm, fossil_utf8_to_mbcs(zSvcName), SERVICE_ALL_ACCESS); |
| 825 | 850 | if( !hSvc ) fossil_fatal(zErrFmt, zSvcName, win32_get_last_errmsg()); |
| 826 | 851 | QueryServiceStatus(hSvc, &sstat); |
| 827 | 852 | |