Skip to content

Instantly share code, notes, and snippets.

@fy0
Last active August 16, 2018 01:48
Show Gist options
  • Save fy0/74cc4cc3bee68debcccb102c81ed47a7 to your computer and use it in GitHub Desktop.
Save fy0/74cc4cc3bee68debcccb102c81ed47a7 to your computer and use it in GitHub Desktop.
package main
import (
"context"
"errors"
"fmt"
"io"
"log"
"net/rpc"
"net/rpc/jsonrpc"
"os"
"os/exec"
"path/filepath"
"time"
"github.com/kbinani/win"
)
var uiProcessCancel context.CancelFunc
func getProgramPath() string {
fn, err := filepath.Abs(os.Args[0])
if err != nil {
panic(err)
}
return fn
}
type ReadWriteCloser struct {
io.ReadCloser
io.WriteCloser
}
func (rw *ReadWriteCloser) Close() error {
rw.ReadCloser.Close()
rw.WriteCloser.Close()
return nil
}
type Adder int
var no int
// Returns how many times the function has been called.
func (p *Adder) Add(in *Adder, ret *int) error {
no++
*p += *in + 2
*in = *p
return nil
}
func CreateNamedPipe() (r *os.File, w *os.File, err error) {
// 参数2:
// PIPE_ACCESS_DUPLEX 0x03
// 参数3:
// FILE_FLAG_OVERLAPPED 0x40000000
// PIPE_TYPE_BYTE 0
// 倒数第二个:
// PIPE_WAIT 0x00000000
hPipe := win.CreateNamedPipe("\\\\.\\pipe\\testName", 0x00000003, 0, 1, 1024, 1024, 0, nil)
hPipe2 := win.CreateNamedPipe("\\\\.\\pipe\\testName2", 0x00000003, 0, 1, 1024, 1024, 0, nil)
win.ConnectNamedPipe(hPipe, nil)
win.ConnectNamedPipe(hPipe2, nil)
return os.NewFile(uintptr(hPipe), "|0"), os.NewFile(uintptr(hPipe2), "|1"), nil
}
func OpenNamedPipe() (r *os.File, w *os.File, err error) {
// OPEN_EXISTING 3
hPipe := win.CreateFile("\\\\.\\pipe\\testName", 0x80000000|0x40000000, 0, nil, 3, 0, 0)
hPipe2 := win.CreateFile("\\\\.\\pipe\\testName2", 0x80000000|0x40000000, 0, nil, 3, 0, 0)
if hPipe2 != 0xffffffff {
return os.NewFile(uintptr(hPipe), "|0"), os.NewFile(uintptr(hPipe2), "|1"), nil
}
return nil, nil, errors.New("err")
}
func main() {
var curProgress = "main"
if len(os.Args) >= 2 {
if os.Args[1] == "UI-PROCESS" {
curProgress = "ui"
}
}
switch curProgress {
case "main":
var ctx context.Context
ctx, uiProcessCancel = context.WithCancel(context.Background())
uiprogress := exec.CommandContext(ctx, getProgramPath(), "UI-PROCESS")
uiprogress.Start()
var err error
rwc := new(ReadWriteCloser)
rwc.ReadCloser, rwc.WriteCloser, err = CreateNamedPipe()
fmt.Println("linked")
if err != nil {
log.Fatal(err)
}
serv := rpc.NewServer()
codec := jsonrpc.NewServerCodec(rwc)
m := new(Adder)
serv.Register(m)
fmt.Println("Registered adder service")
go serv.ServeCodec(codec)
time.Sleep(3 * time.Second)
fmt.Printf("Adder has been called %d times and is now: %d\n", no, *m)
time.Sleep(30 * time.Second)
case "ui":
fmt.Println("ui progress")
var err error
adder := Adder(1)
var ret int
rwc := new(ReadWriteCloser)
rwc.WriteCloser, rwc.ReadCloser, err = OpenNamedPipe()
client := jsonrpc.NewClient(rwc)
fmt.Println(client)
for i := 0; i < 3; i++ {
err = client.Call("Adder.Add", &adder, &ret)
if err != nil {
log.Fatal(err)
}
}
time.Sleep(30 * time.Second)
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment