Пример #1
2
func GetProcessNameMap() map[uint32]string {
	defer metrics("GetProcessNameMap")(time.Now())
	snapshot, err := syscall.CreateToolhelp32Snapshot(syscall.TH32CS_SNAPPROCESS, 0)
	if err != nil {
		common.Error("Fail to syscall CreateToolhelp32Snapshot: %v", err)
		return nil
	}
	defer syscall.CloseHandle(snapshot)
	var procEntry syscall.ProcessEntry32
	procEntry.Size = uint32(unsafe.Sizeof(procEntry))
	if err = syscall.Process32First(snapshot, &procEntry); err != nil {
		common.Error("Fail to syscall Process32First: %v", err)
		return nil
	}
	processNameMap := make(map[uint32]string)
	for {
		processNameMap[procEntry.ProcessID] = parseProcessName(procEntry.ExeFile)
		if err = syscall.Process32Next(snapshot, &procEntry); err != nil {
			if err == syscall.ERROR_NO_MORE_FILES {
				return processNameMap
			}
			common.Error("Fail to syscall Process32Next: %v", err)
			return nil
		}
	}
}
Пример #2
0
// netstat -ano | findstr 202.89.233.104
func getTCPTable() *MIB_TCPTABLE2 {
	getTCPTable2 := syscall.NewLazyDLL("Iphlpapi.dll").NewProc("GetTcpTable2")
	var n uint32
	if err, _, _ := getTCPTable2.Call(uintptr(unsafe.Pointer(&MIB_TCPTABLE2{})), uintptr(unsafe.Pointer(&n)), 1); syscall.Errno(err) != syscall.ERROR_INSUFFICIENT_BUFFER {
		common.Error("Error calling GetTcpTable2: %v", syscall.Errno(err))
	}
	b := make([]byte, n)
	if err, _, _ := getTCPTable2.Call(uintptr(unsafe.Pointer(&b[0])), uintptr(unsafe.Pointer(&n)), 1); err != 0 {
		common.Error("Error calling GetTcpTable2: %v", syscall.Errno(err))
	}
	table := newTCPTable(NewClassReader(b))
	return table
}
Пример #3
0
func doProcess() bool {
	success := true
	hostsIPMap := getHostsIpMap()
	overwriteSystemHosts()
	processNameMap := GetProcessNameMap()
	table := getTCPTable()
	for i := uint32(0); i < uint32(table.dwNumEntries); i++ {
		row := table.table[i]
		ip := row.displayIP(row.dwRemoteAddr)
		port := row.displayPort(row.dwRemotePort)
		if row.dwOwningPid <= 0 {
			continue
		}
		if port != 80 && port != 443 {
			continue
		}
		process := strings.ToLower(processNameMap[uint32(row.dwOwningPid)])
		if hostsIPMap[ip] || common.BrowserMap[process] {
			if err := CloseTCPEntry(row); err != nil {
				common.Error("Fail to close TCP connections: Process = %v, Pid = %v, Addr = %v:%v", process, row.dwOwningPid, ip, port)
				success = false
			} else {
				common.Info("Succeed to close TCP connections: Process = %v, Pid = %v, Addr = %v:%v", process, row.dwOwningPid, ip, port)
			}
		}
	}
	return success
}
Пример #4
0
func overwriteSystemHosts() {
	bytes := ReadCurrentHostConfig()
	if bytes == nil {
		return
	}
	if err := ioutil.WriteFile(systemHosts, bytes, os.ModeExclusive); err != nil {
		common.Error("Error writing to system hosts file: ", err)
	}
}
Пример #5
0
func watchPidFile() {
	batcher, err := New(time.Millisecond * 50)
	if err != nil {
		common.Error("Fail to initialize batcher")
		return
	}
	if err := batcher.Add(pidFilePath); err != nil {
		common.Error("Fail to add pid file: %s", pidFilePath)
		return
	}
	for events := range batcher.Events {
		for _, event := range events {
			if event.Op&fsnotify.Write == fsnotify.Write {
				common.Info("modified file: %v", event)
				trigger <- true
				break
			}
		}
	}
}
Пример #6
0
func newTextEdit() TextEdit {
	return TextEdit{
		AssignTo:      &(context.hostConfigText),
		StretchFactor: 3,
		OnKeyUp: func(key walk.Key) {
			current := context.treeView.CurrentItem()
			if current != nil {
				file := "conf/hosts/" + current.Text() + ".hosts"
				if err := ioutil.WriteFile(file, []byte(context.hostConfigText.Text()), os.ModeExclusive); err != nil {
					common.Error("Error writing to system hosts file: ", err)
				}
			}
		},
	}
}
Пример #7
0
func newNotify() {
	var err error
	context.notifyIcon, err = walk.NewNotifyIcon()
	if err != nil {
		common.Error("Error invoking NewNotifyIcon: %v", err)
	}
	icon, _ := walk.NewIconFromFile("res/lily.ico")
	if err := context.notifyIcon.SetIcon(icon); err != nil {
		common.Error("Error setting notify icon: %v", err)
	}
	if err := context.notifyIcon.SetToolTip("Click for info or use the context menu to exit."); err != nil {
		common.Error("Fail to set tooltip: %v", err)
	}
	f := func() {
		if !context.mw.Visible() {
			context.mw.Show()
		} else {
			context.mw.SwitchToThisWindow()
		}
	}
	go core.Triggered(f)
	context.notifyIcon.MouseUp().Attach(func(x, y int, button walk.MouseButton) {
		if button == walk.LeftButton {
			f()
		}
		// if err := context.notifyIcon.ShowCustom(
		// 	"Walk NotifyIcon Example",
		// 	"There are multiple ShowX methods sporting different icons."); err != nil {
		// 	common.Error("Fail to show custom notify: %v", err)
		// }
	})
	exitAction := walk.NewAction()
	if err := exitAction.SetText("退出"); err != nil {
		common.Error("Error setting exitAction text: %v", err)
	}
	exitAction.Triggered().Attach(func() {
		context.notifyIcon.Dispose()
		// os.Exit(-1)
		walk.App().Exit(0)
	})
	if err := context.notifyIcon.ContextMenu().Actions().Add(exitAction); err != nil {
		common.Error("Error Adding exitAction: %v", err)
	}
	if err := context.notifyIcon.SetVisible(true); err != nil {
		common.Error("Error setting notify visible: %v", err)
	}
	// if err := context.notifyIcon.ShowInfo("Walk NotifyIcon Example", "Click the icon to show again."); err != nil {
	// 	common.Error("Error showing info: %v", err)
	// }
}
Пример #8
0
func readHostConfigMap(path string) map[string]string {
	hostConfigMap := make(map[string]string)
	file, err := os.Open(path)
	if err != nil {
		common.Info("Fail to open system_hosts: %s", err)
	}
	defer file.Close()
	scanner := bufio.NewScanner(file)
	for scanner.Scan() {
		line := strings.TrimSpace(scanner.Text())
		if line != "" && !strings.HasPrefix(line, "#") {
			config := strings.Fields(line)
			if len(config) == 2 {
				hostConfigMap[config[1]] = config[0]
			}
		}
	}
	if err := scanner.Err(); err != nil {
		common.Error("Fail to read system_hosts: %s", err)
	}
	return hostConfigMap
}
Пример #9
0
func writePidFile(pid int) {
	if err := ioutil.WriteFile(pidFilePath, []byte(fmt.Sprint(pid)), os.ModeExclusive); err != nil {
		common.Error("Error writing to system hosts file: ", err)
	}
}
Пример #10
0
func newToolBar() ToolBar {
	tb := ToolBar{
		ButtonStyle: ToolBarButtonImageBeforeText,
		Items: []MenuItem{
			Action{
				AssignTo: &(context.addButton),
				Text:     "新增",
				Image:    "res/add.png",
				// Enabled: Bind("isSpecialMode && enabledCB.Checked"),
				OnTriggered: func() {
					var dlg *walk.Dialog
					var hostsNameEdit *walk.LineEdit
					Dialog{
						AssignTo: &dlg,
						Title:    "新增",
						MinSize:  Size{300, 150},
						Layout:   VBox{},
						Children: []Widget{
							Composite{
								Layout: Grid{Columns: 2},
								Children: []Widget{
									Label{
										ColumnSpan: 2,
										Text:       "Hosts名字:",
									},
									LineEdit{
										AssignTo:   &hostsNameEdit,
										ColumnSpan: 2,
										// Text:       Bind("PatienceField"),
									},
								},
							},
							HSpacer{},
							Composite{
								Layout: HBox{},
								Children: []Widget{
									PushButton{
										// AssignTo: &acceptPB,
										Text: "确定",
										OnClicked: func() {
											// if err := db.Submit(); err != nil {
											// 	log.Print(err)
											// 	return
											// }
											item := &model.HostConfigItem{Name: hostsNameEdit.Text(), Icon: common.IconMap[common.ICON_NEW]}
											conf.Config.HostConfigModel.Insert(item)
											context.treeView.SetCurrentItem(item)
											dlg.Accept()
										},
									},
									PushButton{
										// AssignTo:  &cancelPB,
										Text:      "取消",
										OnClicked: func() { dlg.Cancel() },
									},
								},
							},
						},
					}.Run(context.mw)
				},
			},
			//FIXME 去除刷新按钮是因为点击以后, 双击hosts不再生效
			// Action{
			// 	Text:  "刷新",
			// 	Image: "res/refresh.png",
			// 	// Enabled: Bind("isSpecialMode && enabledCB.Checked"),
			// 	OnTriggered: func() {
			// 		conf.Load()
			// 	},
			// },
			// Action{
			// 	Text:  "修改",
			// 	Image: "res/pencil.png",
			// 	// Enabled: Bind("isSpecialMode && enabledCB.Checked"),
			// 	// OnTriggered: mw.specialAction_Triggered,
			// },
			Action{
				AssignTo: &(context.deleteButton),
				Text:     "删除",
				Image:    "res/delete.png",
				// Enabled: Bind("isSpecialMode && enabledCB.Checked"),
				OnTriggered: func() {
					if context.treeView.CurrentItem() == nil {
						walk.MsgBox(context.mw, "删除hosts", "请选择左边列表后再删除", walk.MsgBoxIconInformation)
						context.deleteButton.SetEnabled(false)
						return
					}
					current := context.treeView.CurrentItem().(*model.HostConfigItem)
					message := fmt.Sprintf("确定要删除hosts '%s'?", current.Text())
					ret := walk.MsgBox(context.mw, "删除hosts", message, walk.MsgBoxYesNo)
					if ret == win.IDYES {
						if !conf.Config.HostConfigModel.Remove(current) {
							common.Error("Fail to remove current item: %v", current.Text())
							// TODO notify user
							return
						}
						if context.treeView.Model().RootCount() > 0 {
							context.treeView.SetCurrentItem(context.treeView.Model().RootAt(0))
						}
						file := "conf/hosts/" + current.Text() + ".hosts"
						if err := os.Remove(file); err != nil {
							common.Error("Fail to delete file: %s", file)
							// TODO notify user
							return
						}
						common.Info("Succeed to delete file: %s", file)
					}
				},
			},
		},
	}
	return tb
}