1// Copyright 2015 Keybase, Inc. All rights reserved. Use of
2// this source code is governed by the included BSD license.
3
4// +build windows
5
6package libkb
7
8import (
9	"os"
10	"os/exec"
11	"syscall"
12	"testing"
13)
14
15func exists(name string) bool {
16	_, err := os.Stat(name)
17	return !os.IsNotExist(err)
18}
19
20// run runs arg command. It returns error if command could not be run.
21// If command did run, the function will return error == nil and
22// integer command exit code.
23func run(arg ...string) (int, error) {
24	err := exec.Command(arg[0], arg[1:]...).Run()
25	if err != nil {
26		if e2, ok := err.(*exec.ExitError); ok {
27			if s, ok := e2.Sys().(syscall.WaitStatus); ok {
28				return int(s.ExitCode), nil
29			}
30		}
31		return 0, err
32	}
33	return 0, nil
34}
35
36func TestLockPIDFile_windows(t *testing.T) {
37
38	g := MakeThinGlobalContextForTesting(t)
39	lpFile := NewLockPIDFile(g, "TestLockPIDWin")
40	err := lpFile.Lock()
41
42	if !exists("TestLockPIDWin") {
43		t.Fatalf("LockPIDFile: file creation failed")
44	} else if err != nil {
45		t.Fatalf("LockPIDFile failed: %v", err)
46	} else {
47		// External process should be blocked from deleting the file
48		run("cmd", "/c", "del", "TestLockPIDWin")
49		if !exists("TestLockPIDWin") {
50			t.Fatalf("LockPIDFile: expected error deleting locked file")
51		}
52	}
53	lpFile.Close()
54
55	// External process should be able to delete the file now
56	exitcode, err := run("cmd", "/c", "del", "TestLockPIDWin")
57	if err != nil || exitcode != 0 || exists("TestLockPIDWin") {
58		t.Fatalf("LockPIDFile: exe.Command(del) failed: %v", err)
59	}
60}
61