mtkennerly / shawl

Windows service wrapper for arbitrary commands
MIT License
495 stars 15 forks source link

stop service from gui report error #9

Closed rustbomber closed 3 years ago

rustbomber commented 3 years ago

can start the service through the service properties interface, but when it stops, an error is reported, see windows event log, display:101 The exclusive semaphore is owned by another process.

mtkennerly commented 3 years ago

Thanks for the report! Couple of questions:

I'm not able to reproduce this on my Windows 10 system, so it may be something particular about the wrapped program.

mtkennerly commented 3 years ago

@akaylh Do you have any more information you can share about this? Otherwise, since I can't reproduce it, I would just have to close the ticket, unfortunately.

ross-oreto commented 1 year ago

I am also seeing this issue. Any service I create with shawl:

One of the Windows event log reports: "The a test service service terminated with the following service-specific error: Attempt to use a file handle to an open disk partition for an operation other than raw disk I/O."

mtkennerly commented 1 year ago

This worked for me on Windows 11 with OpenJDK 18.0.1.1. Could you try the following test, and if it also fails, then could you share your Shawl log files?

ross-oreto commented 1 year ago

Hi, thanks @mtkennerly. That bit will work, the start portion and the java application runs fine. The part that throws an error is when you use the Windows GUI service manager to stop the service, which we also use to start the service. Upon stopping the service with the services GUI, Windows throws an error even though the actual java application is stopping gracefully and hitting its shutdown hooks. For some reason Windows thinks something goes and reports an error wrong even though everything we needed to happen starting and stopping the java web app, was fine.

ross-oreto commented 1 year ago

@mtkennerly Another note is that if I just "sc", it starts and stops as expected and no specific errors are reported if I run sc query afterwards. This seems to be an issue just with using the GUI and makes the user think something is wrong.

mtkennerly commented 1 year ago

Ah, I see. Maybe it's using a weird exit code? Some things to check:

ross-oreto commented 1 year ago

CMD output of sc: TYPE : 10 WIN32_OWN_PROCESS STATE : 1 STOPPED WIN32_EXIT_CODE : 1066 (0x42a) SERVICE_EXIT_CODE : 130 (0x82) CHECKPOINT : 0x0 WAIT_HINT : 0x0

manually running java app: $LASTEXITCODE -1073741510

No custom shutdown hooks, just logging when the server is shutting down which is built into the framework, which in this case is Micronaut and or vert.x.

ross-oreto commented 1 year ago

It's possible that after the application is already shutdown, the logger tries to log an entry about shutting down, but the stream is already closed and that throws an error exit code. If you use the GUI on your test app, do you see a Windows error or is it clean?

Never mind, I just realized that test app doesn't stay open as web application so stopping in that case won't matter.

mtkennerly commented 1 year ago

If I modify it to keep running in a loop, then I get the same exit codes as you, but a different error in the GUI:

image

I think your idea about the server logging sounds plausible. Some custom shutdown code might help. For example, the following exits with 0, so the services GUI doesn't complain:

import java.io.*;
import java.lang.*;
import java.nio.file.*;

class JTest {
    public static void main(String[] args) {
        System.out.println("Hello, World!"); 

        Runtime.getRuntime().addShutdownHook(new Thread() {
            public void run() {
                System.out.println("Exiting");
                Runtime.getRuntime().halt(0);
            }
        });

        try {
            while (true) {
                Files.write(Paths.get("log.txt"), "\ntest".getBytes(), StandardOpenOption.APPEND);
                Thread.sleep(100);
            }
        } catch (IOException e) {
            System.out.println("io");
            System.out.println(e);
        } catch (InterruptedException e) {
            System.out.println("interrupted");
            System.out.println(e);
        }
    }
}

Shawl log:

2023-06-07 09:47:26 [DEBUG] ********** LAUNCH **********
2023-06-07 09:47:26 [DEBUG] Cli { sub: Run { common: CommonOpts { pass: None, restart: false, no_restart: false, restart_if: [], restart_if_not: [], stop_timeout: None, no_log: false, no_log_cmd: false, log_dir: None, pass_start_args: false, env: [], path: [], command: ["C:\\opt\\jdk-18.0.1.1\\bin\\java.exe", "-jar", "JTest.jar"] }, cwd: Some("\\\\?\\C:\\tmp\\jtest"), name: "a test service" } }
2023-06-07 09:47:26 [DEBUG] Entering main service loop
2023-06-07 09:47:26 [INFO] Launching command
2023-06-07 09:47:26 [DEBUG] stdout: "Hello, World!"
2023-06-07 09:47:32 [INFO] Received stop event
2023-06-07 09:47:32 [INFO] Sending ctrl-C to command
2023-06-07 09:47:32 [DEBUG] stdout: "Exiting"
2023-06-07 09:47:33 [INFO] Command exited after 63 ms with code 0
2023-06-07 09:47:33 [DEBUG] Exited main service loop
2023-06-07 09:47:33 [DEBUG] Finished successfully