experimental realms / citadel integration

shw-merge
dma 6 years ago
parent 20c648026a
commit 76b194840a

@ -17,8 +17,8 @@ import (
"io/ioutil" "io/ioutil"
"os" "os"
"os/signal" "os/signal"
"strings"
"strconv" "strconv"
"strings"
"sync" "sync"
"syscall" "syscall"
"time" "time"
@ -29,6 +29,8 @@ import (
"github.com/gotk3/gotk3/gdk" "github.com/gotk3/gotk3/gdk"
"github.com/gotk3/gotk3/glib" "github.com/gotk3/gotk3/glib"
"github.com/gotk3/gotk3/gtk" "github.com/gotk3/gotk3/gtk"
"github.com/godbus/dbus"
) )
type promptModes uint type promptModes uint
@ -55,6 +57,7 @@ type appShortcuts struct {
type cbPromptAdd func(guid, path, icon, proto string, pid int, ipaddr, hostname string, port, uid, gid int, type cbPromptAdd func(guid, path, icon, proto string, pid int, ipaddr, hostname string, port, uid, gid int,
origin, timestamp string, is_socks bool, optstring string, sandbox string, action int) bool origin, timestamp string, is_socks bool, optstring string, sandbox string, action int) bool
type cbPromptRemove func(string) type cbPromptRemove func(string)
var cbPromptAddRequest cbPromptAdd = nil var cbPromptAddRequest cbPromptAdd = nil
var cbPromptRemoveRequest cbPromptRemove = nil var cbPromptRemoveRequest cbPromptRemove = nil
@ -66,64 +69,63 @@ type fwApp struct {
forceMenu bool forceMenu bool
Dbus *dbusObject Dbus *dbusObject
DbusServer *dbusServer DbusServer *dbusServer
promptMode promptModes promptMode promptModes
prompt *Prompt prompt *Prompt
Config *sgfw.FirewallConfigs Config *sgfw.FirewallConfigs
Settings *settings.Settings Settings *settings.Settings
winb *builder winb *builder
win *gtk.ApplicationWindow win *gtk.ApplicationWindow
repopMutex *sync.Mutex repopMutex *sync.Mutex
swRulesPermanent *gtk.ScrolledWindow swRulesPermanent *gtk.ScrolledWindow
swRulesSession *gtk.ScrolledWindow swRulesSession *gtk.ScrolledWindow
swRulesProcess *gtk.ScrolledWindow swRulesProcess *gtk.ScrolledWindow
swRulesSystem *gtk.ScrolledWindow swRulesSystem *gtk.ScrolledWindow
swPrompt *gtk.ScrolledWindow swPrompt *gtk.ScrolledWindow
boxPermanent *gtk.ListBox boxPermanent *gtk.ListBox
boxSession *gtk.ListBox boxSession *gtk.ListBox
boxProcess *gtk.ListBox boxProcess *gtk.ListBox
boxSystem *gtk.ListBox boxSystem *gtk.ListBox
rlPermanent *ruleList rlPermanent *ruleList
rlSession *ruleList rlSession *ruleList
rlProcess *ruleList rlProcess *ruleList
rlSystem *ruleList rlSystem *ruleList
btnNewRule *gtk.Button btnNewRule *gtk.Button
nbRules *gtk.Notebook nbRules *gtk.Notebook
tlStack *gtk.Stack tlStack *gtk.Stack
tlStackSwitcher *gtk.StackSwitcher tlStackSwitcher *gtk.StackSwitcher
gridConfig *gtk.Grid gridConfig *gtk.Grid
entrySearch *gtk.SearchEntry entrySearch *gtk.SearchEntry
btnSearch *gtk.ToggleButton btnSearch *gtk.ToggleButton
revealerSearch *gtk.Revealer revealerSearch *gtk.Revealer
boxAppMenu *gtk.Box boxAppMenu *gtk.Box
btnAppMenu *gtk.MenuButton btnAppMenu *gtk.MenuButton
dialog *gtk.MessageDialog dialog *gtk.MessageDialog
signalDelete glib.SignalHandle signalDelete glib.SignalHandle
lcache string lcache string
shortcuts []appShortcuts shortcuts []appShortcuts
userMap map[int32]string userMap map[int32]string
userIDs []int32 userIDs []int32
groupMap map[int32]string groupMap map[int32]string
groupIDs []int32 groupIDs []int32
userMapLock *sync.Mutex userMapLock *sync.Mutex
groupMapLock *sync.Mutex groupMapLock *sync.Mutex
intcount uint intcount uint
ozProfiles []string ozProfiles []string
} }
/* /*
* App Setup * App Setup
*/ */
@ -183,7 +185,7 @@ func (fa *fwApp) initGtk() {
appFlags |= glib.APPLICATION_CAN_OVERRIDE_APP_ID appFlags |= glib.APPLICATION_CAN_OVERRIDE_APP_ID
//appFlags |= glib.APPLICATION_IS_LAUNCHER //appFlags |= glib.APPLICATION_IS_LAUNCHER
//appFlags |= glib.APPLICATION_IS_SERVICE //appFlags |= glib.APPLICATION_IS_SERVICE
app, err := gtk.ApplicationNew("com.subgraph.Firewall.Settings", appFlags)//glib.APPLICATION_FLAGS_NONE) app, err := gtk.ApplicationNew("com.subgraph.Firewall.Settings", appFlags) //glib.APPLICATION_FLAGS_NONE)
if err != nil { if err != nil {
panic(fmt.Sprintf("gtk.ApplicationNew() failed: %v", err)) panic(fmt.Sprintf("gtk.ApplicationNew() failed: %v", err))
} }
@ -241,25 +243,25 @@ func (fa *fwApp) build() {
func (fa *fwApp) registerActions() { func (fa *fwApp) registerActions() {
anr := glib.SimpleActionNew("new_rule", glib.VARIANT_TYPE_NONE) anr := glib.SimpleActionNew("new_rule", glib.VARIANT_TYPE_NONE)
anr.Connect("activate", func () { anr.Connect("activate", func() {
fa.btnNewRule.Activate() fa.btnNewRule.Activate()
}) })
fa.ActionMap.AddAction(&anr.Action) fa.ActionMap.AddAction(&anr.Action)
snr := glib.SimpleActionNew("shortcuts", glib.VARIANT_TYPE_NONE) snr := glib.SimpleActionNew("shortcuts", glib.VARIANT_TYPE_NONE)
snr.Connect("activate", func () { snr.Connect("activate", func() {
fa.showShortcutsWindow() fa.showShortcutsWindow()
}) })
fa.ActionMap.AddAction(&snr.Action) fa.ActionMap.AddAction(&snr.Action)
abnr := glib.SimpleActionNew("about", glib.VARIANT_TYPE_NONE) abnr := glib.SimpleActionNew("about", glib.VARIANT_TYPE_NONE)
abnr.Connect("activate", func() {fa.showAboutDialog()}) abnr.Connect("activate", func() { fa.showAboutDialog() })
fa.ActionMap.AddAction(&abnr.Action) fa.ActionMap.AddAction(&abnr.Action)
/* /*
hbnr := glib.SimpleActionNew("help", glib.VARIANT_TYPE_NONE) hbnr := glib.SimpleActionNew("help", glib.VARIANT_TYPE_NONE)
hbnr.Connect("activate", func() {fmt.Println("UNIMPLEMENTED")}) hbnr.Connect("activate", func() {fmt.Println("UNIMPLEMENTED")})
fa.ActionMap.AddAction(&hbnr.Action) fa.ActionMap.AddAction(&hbnr.Action)
*/ */
qnr := glib.SimpleActionNew("quit", glib.VARIANT_TYPE_NONE) qnr := glib.SimpleActionNew("quit", glib.VARIANT_TYPE_NONE)
qnr.Connect("activate", func() { qnr.Connect("activate", func() {
fa.win.Close() fa.win.Close()
@ -268,18 +270,18 @@ func (fa *fwApp) registerActions() {
} }
func (fa *fwApp) registerShortcuts() { func (fa *fwApp) registerShortcuts() {
fa.ConnectShortcut("<Primary><Alt>Page_Down", "rules", "Go to next rules views", fa.win.Window, func (win gtk.Window) { fa.ConnectShortcut("<Primary><Alt>Page_Down", "rules", "Go to next rules views", fa.win.Window, func(win gtk.Window) {
fa.switchRulesItem(switcherDirectionUp) fa.switchRulesItem(switcherDirectionUp)
}) })
fa.ConnectShortcut("<Primary><Alt>Page_Up", "rules", "Go to previous rules views", fa.win.Window, func (win gtk.Window) { fa.ConnectShortcut("<Primary><Alt>Page_Up", "rules", "Go to previous rules views", fa.win.Window, func(win gtk.Window) {
fa.switchRulesItem(switcherDirectionDown) fa.switchRulesItem(switcherDirectionDown)
}) })
fa.ConnectShortcut("<Primary>n", "rules", "Create new rule", fa.win.Window, func (win gtk.Window) { fa.ConnectShortcut("<Primary>n", "rules", "Create new rule", fa.win.Window, func(win gtk.Window) {
if fa.btnNewRule.GetSensitive() { if fa.btnNewRule.GetSensitive() {
fa.btnNewRule.Emit("clicked") fa.btnNewRule.Emit("clicked")
} }
}) })
fa.ConnectShortcut("<Primary>f", "rules", "Search for rule", fa.win.Window, func (win gtk.Window) { fa.ConnectShortcut("<Primary>f", "rules", "Search for rule", fa.win.Window, func(win gtk.Window) {
if fa.tlStack.GetVisibleChildName() == "rules" { if fa.tlStack.GetVisibleChildName() == "rules" {
reveal := fa.revealerSearch.GetRevealChild() reveal := fa.revealerSearch.GetRevealChild()
if !reveal { if !reveal {
@ -289,31 +291,31 @@ func (fa *fwApp) registerShortcuts() {
fa.entrySearch.Widget.GrabFocus() fa.entrySearch.Widget.GrabFocus()
} }
}) })
fa.ConnectShortcut("<Primary><Shift>Page_Down", "general", "Go to the next view", fa.win.Window, func (win gtk.Window) { fa.ConnectShortcut("<Primary><Shift>Page_Down", "general", "Go to the next view", fa.win.Window, func(win gtk.Window) {
fa.switchStackItem(switcherDirectionDown) fa.switchStackItem(switcherDirectionDown)
}) })
fa.ConnectShortcut("<Primary><Shift>Page_Up", "general", "Go to the previous view", fa.win.Window, func (win gtk.Window) { fa.ConnectShortcut("<Primary><Shift>Page_Up", "general", "Go to the previous view", fa.win.Window, func(win gtk.Window) {
fa.switchStackItem(switcherDirectionUp) fa.switchStackItem(switcherDirectionUp)
}) })
if fa.promptMode != promptModeDisabled { if fa.promptMode != promptModeDisabled {
fa.RegisterShortcutHelp("<Primary><Alt>space", "general", "Answer first firewall prompt") fa.RegisterShortcutHelp("<Primary><Alt>space", "general", "Answer first firewall prompt")
} }
/* /*
fa.ConnectShortcut("<Primary>question", "general", "Show the program help", fa.win.Window, func (win gtk.Window) { fa.ConnectShortcut("<Primary>question", "general", "Show the program help", fa.win.Window, func (win gtk.Window) {
ha := fa.ActionMap.LookupAction("help") ha := fa.ActionMap.LookupAction("help")
if ha != nil { if ha != nil {
ha.Activate(nil) ha.Activate(nil)
} }
}) })
*/ */
fa.ConnectShortcut("F1", "general", "Show this help window", fa.win.Window, func (win gtk.Window) { fa.ConnectShortcut("F1", "general", "Show this help window", fa.win.Window, func(win gtk.Window) {
fa.showShortcutsWindow() fa.showShortcutsWindow()
}) })
fa.ConnectShortcut("<Primary>q", "general", "Exit program", fa.win.Window, func (win gtk.Window) { fa.ConnectShortcut("<Primary>q", "general", "Exit program", fa.win.Window, func(win gtk.Window) {
fa.win.Close() fa.win.Close()
}) })
// Easter Egg // Easter Egg
fa.ConnectShortcut("<Primary>F5", "", "", fa.win.Window, func (win gtk.Window) { fa.ConnectShortcut("<Primary>F5", "", "", fa.win.Window, func(win gtk.Window) {
fa.repopulateWindow() fa.repopulateWindow()
fa.loadConfig(false) fa.loadConfig(false)
}) })
@ -342,12 +344,12 @@ func (fa *fwApp) buildWindow() {
fa.win.SetIconName("security-medium") fa.win.SetIconName("security-medium")
fa.win.SetTitle("Subgraph Firewall Settings") fa.win.SetTitle("Subgraph Firewall Settings")
/* /*
fa.winb.ConnectSignals(map[string]interface{} { fa.winb.ConnectSignals(map[string]interface{} {
"on_changed_search": fa.onChangedSearch, "on_changed_search": fa.onChangedSearch,
"on_stoped_search": fa.onStopedSearch, "on_stoped_search": fa.onStopedSearch,
}) })
*/ */
//fa.swRulesPermanent.Connect("key-press-event", fa.onRulesKeyPress) //fa.swRulesPermanent.Connect("key-press-event", fa.onRulesKeyPress)
fa.entrySearch.Connect("search-changed", fa.onChangedSearch) fa.entrySearch.Connect("search-changed", fa.onChangedSearch)
fa.entrySearch.Connect("stop-search", fa.onStopedSearch) fa.entrySearch.Connect("stop-search", fa.onStopedSearch)
@ -414,7 +416,6 @@ func (fa *fwApp) buildAppMenu() {
} }
} }
/* /*
* Windows * Windows
*/ */
@ -449,7 +450,7 @@ func (fa *fwApp) showPromptQuit() bool {
func (fa *fwApp) showAddRuleDialog() { func (fa *fwApp) showAddRuleDialog() {
rule := &sgfw.DbusRule{} rule := &sgfw.DbusRule{}
rl := &ruleList{app: fa} rl := &ruleList{app: fa}
rr := &ruleRow{ rl: rl, rule: rule} rr := &ruleRow{rl: rl, rule: rule}
rnew := newRuleAdd(rr, DIALOG_MODE_NEW) rnew := newRuleAdd(rr, DIALOG_MODE_NEW)
rnew.update() rnew.update()
rnew.run("", nil) rnew.run("", nil)
@ -479,7 +480,7 @@ func (fa *fwApp) showAboutDialog() {
ad, _ := gtk.AboutDialogNew() ad, _ := gtk.AboutDialogNew()
ad.SetName(sfs) ad.SetName(sfs)
ad.SetProgramName(sfs) ad.SetProgramName(sfs)
ad.SetAuthors([]string{"<a href=\""+url+"\">Subgraph Inc</a>"}) ad.SetAuthors([]string{"<a href=\"" + url + "\">Subgraph Inc</a>"})
//ad.AddCreditSection("", []string{"- Bruce Leidl", "- David Mirza", "- Stephen Watt", "- Matthieu Lalonde"}) //ad.AddCreditSection("", []string{"- Bruce Leidl", "- David Mirza", "- Stephen Watt", "- Matthieu Lalonde"})
ad.SetVersion("0.1.0") ad.SetVersion("0.1.0")
ad.SetCopyright(fmt.Sprintf("© %s.", cs)) ad.SetCopyright(fmt.Sprintf("© %s.", cs))
@ -501,8 +502,8 @@ func (fa *fwApp) showShortcutsWindow() {
var groups = []string{"general", "rules", "prompt"} var groups = []string{"general", "rules", "prompt"}
var titles = map[string]string{ var titles = map[string]string{
"general": "General", "general": "General",
"rules": "Rules", "rules": "Rules",
"prompt": "Firewall Prompt", "prompt": "Firewall Prompt",
} }
xv := new(GtkXMLInterface) xv := new(GtkXMLInterface)
xv.Comment = " interface-requires gtk+ 3.20 " xv.Comment = " interface-requires gtk+ 3.20 "
@ -517,19 +518,19 @@ func (fa *fwApp) showShortcutsWindow() {
xss := new(GtkXMLObject) xss := new(GtkXMLObject)
xss.Class = "GtkShortcutsSection" xss.Class = "GtkShortcutsSection"
xss.Properties = []GtkXMLProperty{ xss.Properties = []GtkXMLProperty{
{Name: "visible", Value: "1"}, {Name: "visible", Value: "1"},
{Name: "section-name", Value: "shortcuts"}, {Name: "section-name", Value: "shortcuts"},
{Name: "max-height", Value: "16"}, {Name: "max-height", Value: "16"},
} }
xsw.Children = append(xsw.Children, GtkXMLChild{Objects: []*GtkXMLObject{xss}}) xsw.Children = append(xsw.Children, GtkXMLChild{Objects: []*GtkXMLObject{xss}})
for _, g := range groups { for _, g := range groups {
xsg := new(GtkXMLObject) xsg := new(GtkXMLObject)
xsg.Class = "GtkShortcutsGroup" xsg.Class = "GtkShortcutsGroup"
xsg.Properties = []GtkXMLProperty{ xsg.Properties = []GtkXMLProperty{
{Name: "title", Value: titles[g], Translatable: "yes"}, {Name: "title", Value: titles[g], Translatable: "yes"},
{Name: "visible", Value: "1"}, {Name: "visible", Value: "1"},
} }
found := false found := false
for _, sc := range fa.shortcuts { for _, sc := range fa.shortcuts {
if sc.Group != g { if sc.Group != g {
@ -539,10 +540,10 @@ func (fa *fwApp) showShortcutsWindow() {
xps := new(GtkXMLObject) xps := new(GtkXMLObject)
xps.Class = "GtkShortcutsShortcut" xps.Class = "GtkShortcutsShortcut"
xps.Properties = []GtkXMLProperty{ xps.Properties = []GtkXMLProperty{
{Name: "visible", Value: "yes"}, {Name: "visible", Value: "yes"},
{Name: "accelerator", Value: sc.Accel}, {Name: "accelerator", Value: sc.Accel},
{Name: "title", Translatable: "yes", Value: sc.Title}, {Name: "title", Translatable: "yes", Value: sc.Title},
} }
xsg.Children = append(xsg.Children, GtkXMLChild{Objects: []*GtkXMLObject{xps}}) xsg.Children = append(xsg.Children, GtkXMLChild{Objects: []*GtkXMLObject{xps}})
} }
if found { if found {
@ -573,7 +574,6 @@ func (fa *fwApp) showShortcutsWindow() {
} }
} }
/* /*
* Private Utils * Private Utils
*/ */
@ -592,7 +592,6 @@ func (fa *fwApp) populateWindow() {
fa.rlPermanent.loadRules(true) fa.rlPermanent.loadRules(true)
fa.rlPermanent.reloadRules(tt) fa.rlPermanent.reloadRules(tt)
if fa.boxSession == nil { if fa.boxSession == nil {
fa.boxSession, _ = gtk.ListBoxNew() fa.boxSession, _ = gtk.ListBoxNew()
fa.swRulesSession.Add(fa.boxSession) fa.swRulesSession.Add(fa.boxSession)
@ -605,7 +604,6 @@ func (fa *fwApp) populateWindow() {
fa.rlSession.loadRules(true) fa.rlSession.loadRules(true)
fa.rlSession.reloadRules(tt) fa.rlSession.reloadRules(tt)
if fa.boxProcess == nil { if fa.boxProcess == nil {
fa.boxProcess, _ = gtk.ListBoxNew() fa.boxProcess, _ = gtk.ListBoxNew()
fa.swRulesProcess.Add(fa.boxProcess) fa.swRulesProcess.Add(fa.boxProcess)
@ -630,38 +628,37 @@ func (fa *fwApp) populateWindow() {
fa.rlSystem.loadRules(true) fa.rlSystem.loadRules(true)
fa.rlSystem.reloadRules(tt) fa.rlSystem.reloadRules(tt)
} }
func (fa *fwApp) repopulateWindow() { func (fa *fwApp) repopulateWindow() {
fmt.Println("Refreshing firewall rule list.") fmt.Println("Refreshing firewall rule list.")
fa.repopMutex.Lock() fa.repopMutex.Lock()
defer fa.repopMutex.Unlock() defer fa.repopMutex.Unlock()
/* /*
child, err := fa.swRulesPermanent.GetChild() child, err := fa.swRulesPermanent.GetChild()
if err != nil { if err != nil {
failDialog(&fa.win.Window, "Unable to clear out permanent rules list display: %v", err) failDialog(&fa.win.Window, "Unable to clear out permanent rules list display: %v", err)
} }
fa.swRulesPermanent.Remove(child) fa.swRulesPermanent.Remove(child)
child, err = fa.swRulesSession.GetChild() child, err = fa.swRulesSession.GetChild()
if err != nil { if err != nil {
failDialog(&fa.win.Window, "Unable to clear out session rules list display: %v", err) failDialog(&fa.win.Window, "Unable to clear out session rules list display: %v", err)
} }
fa.swRulesSession.Remove(child) fa.swRulesSession.Remove(child)
child, err = fa.swRulesProcess.GetChild() child, err = fa.swRulesProcess.GetChild()
if err != nil { if err != nil {
failDialog(&fa.win.Window, "Unable to clear out process rules list display: %v", err) failDialog(&fa.win.Window, "Unable to clear out process rules list display: %v", err)
} }
fa.swRulesProcess.Remove(child) fa.swRulesProcess.Remove(child)
child, err = fa.swRulesSystem.GetChild() child, err = fa.swRulesSystem.GetChild()
if err != nil { if err != nil {
failDialog(&fa.win.Window, "Unable to clear out system rules list display: %v", err) failDialog(&fa.win.Window, "Unable to clear out system rules list display: %v", err)
} }
fa.swRulesSystem.Remove(child) fa.swRulesSystem.Remove(child)
*/ */
if fa.tlStack.GetVisibleChildName() != "rules" && fa.promptMode == promptModeDisabled { if fa.tlStack.GetVisibleChildName() != "rules" && fa.promptMode == promptModeDisabled {
stack := fa.tlStack.GetChildByName("rules") stack := fa.tlStack.GetChildByName("rules")
err := fa.tlStack.ChildSetProperty(stack, "needs-attention", true) err := fa.tlStack.ChildSetProperty(stack, "needs-attention", true)
@ -701,7 +698,7 @@ func (fa *fwApp) switchStackItem(dir switcherDirection) {
stacks := []string{"prompt", "rules", "config"} stacks := []string{"prompt", "rules", "config"}
stacksByName := map[string]int{ stacksByName := map[string]int{
"prompt": 0, "prompt": 0,
"rules": 1, "rules": 1,
"config": 2, "config": 2,
} }
if fa.promptMode == promptModeDisabled { if fa.promptMode == promptModeDisabled {
@ -727,7 +724,6 @@ func (fa *fwApp) switchStackItem(dir switcherDirection) {
fa.onStackChanged() fa.onStackChanged()
} }
/* /*
* Handlers * Handlers
*/ */
@ -738,7 +734,7 @@ func (fa *fwApp) handleSignals(c <-chan os.Signal) {
switch sig { switch sig {
case syscall.SIGINT: case syscall.SIGINT:
if fa.intcount == 0 { if fa.intcount == 0 {
glib.IdleAdd(func () bool { glib.IdleAdd(func() bool {
fa.win.Close() fa.win.Close()
return false return false
}) })
@ -780,7 +776,7 @@ func (fa *fwApp) onWindowDelete() bool {
} }
func (fa *fwApp) onStackChanged() { func (fa *fwApp) onStackChanged() {
tn := fa.tlStack.GetVisibleChildName() tn := fa.tlStack.GetVisibleChildName()
nra := fa.ActionMap.LookupAction("new_rule") nra := fa.ActionMap.LookupAction("new_rule")
if tn == "rules" { if tn == "rules" {
fa.btnNewRule.SetSensitive(true) fa.btnNewRule.SetSensitive(true)
@ -803,7 +799,7 @@ tn := fa.tlStack.GetVisibleChildName()
nra.SetProperty("enabled", false) nra.SetProperty("enabled", false)
} }
if fa.prompt != nil && tn != "prompt"{ if fa.prompt != nil && tn != "prompt" {
pstack := fa.tlStack.GetChildByName("prompt") pstack := fa.tlStack.GetChildByName("prompt")
nag, _ := fa.tlStack.ChildGetProperty(pstack, "needs-attention", glib.TYPE_BOOLEAN) nag, _ := fa.tlStack.ChildGetProperty(pstack, "needs-attention", glib.TYPE_BOOLEAN)
if fa.prompt.HasItems() && !nag.(bool) { if fa.prompt.HasItems() && !nag.(bool) {
@ -853,7 +849,6 @@ func (fa *fwApp) onRulesKeyPress(i interface{}, e *gdk.Event) bool {
return true return true
} }
/* /*
* Users, Groups * Users, Groups
*/ */
@ -867,7 +862,7 @@ func (fa *fwApp) cacheUsers() error {
fa.userMapLock.Lock() fa.userMapLock.Lock()
defer fa.userMapLock.Unlock() defer fa.userMapLock.Unlock()
readColonFile(f, func (line []byte) { readColonFile(f, func(line []byte) {
t := strings.Split(string(line), ":") t := strings.Split(string(line), ":")
id, _ := strconv.ParseInt(t[2], 10, 32) id, _ := strconv.ParseInt(t[2], 10, 32)
fa.userMap[int32(id)] = t[0] fa.userMap[int32(id)] = t[0]
@ -886,7 +881,7 @@ func (fa *fwApp) cacheGroups() error {
fa.groupMapLock.Lock() fa.groupMapLock.Lock()
defer fa.groupMapLock.Unlock() defer fa.groupMapLock.Unlock()
readColonFile(f, func (line []byte) { readColonFile(f, func(line []byte) {
t := strings.Split(string(line), ":") t := strings.Split(string(line), ":")
id, _ := strconv.ParseInt(t[2], 10, 32) id, _ := strconv.ParseInt(t[2], 10, 32)
fa.groupMap[int32(id)] = t[0] fa.groupMap[int32(id)] = t[0]
@ -895,7 +890,6 @@ func (fa *fwApp) cacheGroups() error {
return nil return nil
} }
/* /*
* Exported * Exported
*/ */
@ -918,14 +912,23 @@ func (fa *fwApp) ConnectShortcut(accel, group, title string, w gtk.Window, actio
}) })
w.AddAccelGroup(gr) w.AddAccelGroup(gr)
w.Connect("delete-event", func () bool { w.Connect("delete-event", func() bool {
w.RemoveAccelGroup(gr) w.RemoveAccelGroup(gr)
return false return false
}) })
} }
func (fa *fwApp) LookupUsername(uid int32) string { func (fa *fwApp) LookupUsername(realm string, uid int32) string {
// TODO: needs to be realm aware // TODO: needs to be realm aware
// TODO: cache ^^
if realm != "" {
user := ""
var db, _ = dbus.SystemBus()
obj := db.Object("com.subgraph.realms", "/")
obj.Call("com.subgraph.realms.Manager.RealmUsernameFromUID", 0, realm, strconv.Itoa(int(uid))).Store(&user)
return user
}
if uid == -1 { if uid == -1 {
return "any" return "any"
} }
@ -938,8 +941,17 @@ func (fa *fwApp) LookupUsername(uid int32) string {
return "unknown" return "unknown"
} }
func (fa *fwApp) LookupGroup(gid int32) string { func (fa *fwApp) LookupGroup(realm string, gid int32) string {
// TODO: needs to be realm aware // TODO: needs to be realm aware
// ^^ cache
if realm != "" {
group := ""
var db, _ = dbus.SystemBus()
obj := db.Object("com.subgraph.realms", "/")
obj.Call("com.subgraph.realms.Manager.RealmGroupnameFromGID", 0, realm, strconv.Itoa(int(gid))).Store(&group)
return group
}
if gid == -1 { if gid == -1 {
return "any" return "any"
} }
@ -952,7 +964,6 @@ func (fa *fwApp) LookupGroup(gid int32) string {
return "unknown" return "unknown"
} }
/* /*
* Global Utils * Global Utils
*/ */
@ -990,7 +1001,6 @@ func readColonFile(r io.Reader, fn func(line []byte)) (v interface{}, err error)
return nil, bs.Err() return nil, bs.Err()
} }
/* /*
* Main * Main
*/ */

@ -226,13 +226,13 @@ func (rr *ruleRow) update() {
tt = tt + " for " tt = tt + " for "
} }
if rr.rule.UID > -1 { if rr.rule.UID > -1 {
tt = tt + rr.rl.app.LookupUsername(rr.rule.UID) tt = tt + rr.rl.app.LookupUsername(rr.rule.Sandbox, rr.rule.UID)
} }
if rr.rule.UID > -1 && rr.rule.GID > -1 { if rr.rule.UID > -1 && rr.rule.GID > -1 {
tt = tt + ":" tt = tt + ":"
} }
if rr.rule.GID > -1 { if rr.rule.GID > -1 {
tt = tt + rr.rl.app.LookupGroup(rr.rule.GID) tt = tt + rr.rl.app.LookupGroup(rr.rule.Sandbox, rr.rule.GID)
} }
rr.gtkLabelTarget.SetText(tt) rr.gtkLabelTarget.SetText(tt)
} }

@ -9,6 +9,8 @@ const St = imports.gi.St;
const CheckBox = imports.ui.checkBox const CheckBox = imports.ui.checkBox
const ModalDialog = imports.ui.modalDialog; const ModalDialog = imports.ui.modalDialog;
const Tweener = imports.ui.tweener; const Tweener = imports.ui.tweener;
const Extension = imports.misc.extensionUtils.getCurrentExtension();
const Misc = Extension.imports.misc;
const RuleScope = { const RuleScope = {
APPLY_SESSION: 0, APPLY_SESSION: 0,
@ -22,36 +24,47 @@ const DetailSection = new Lang.Class({
Name: 'DetailSection', Name: 'DetailSection',
_init: function(sandboxed) { _init: function(sandboxed) {
this.actor = new St.BoxLayout({ style_class: 'fw-details-section' }); //this.actor = new St.BoxLayout({ style_class: 'fw-details-section', pack_start: false });
this._left = new St.BoxLayout({ vertical: true, style_class: 'fw-details-left'}); this.actor = new St.BoxLayout({ style_class: 'fw-details-section-container', pack_start: false });
this._cont = new St.BoxLayout({ style_class: 'fw-details-section' });
this._left = new St.BoxLayout({ vertical: true, style_class: 'fw-details-left' });
//this._right = new St.BoxLayout({ vertical: true, style_class: 'fw-details-right' });
this._right = new St.BoxLayout({ vertical: true, style_class: 'fw-details-right' }); this._right = new St.BoxLayout({ vertical: true, style_class: 'fw-details-right' });
this.actor.add_child(this._left); this._more = new St.BoxLayout({ vertical: true, style_class: 'fw-details-right', y_align: Clutter.ActorAlign.CENTER, x_align: St.Align.END });
this.actor.add_child(this._right); this._cont.add_child(this._left);
this._cont.add_child(this._right);
this.actor.add_child(this._cont);
this.actor.add_child(this._more);
//this.actor.add_child(this._left);
//this.actor.add_child(this._right);
//this.actor.add_child(this._more);
if (sandboxed) {
this.sandbox = this._addDetails("Realm:");
}
this.ipAddr = this._addDetails("IP Address:"); this.ipAddr = this._addDetails("IP Address:");
this.path = this._addDetails("Path:"); this.path = this._addDetails("Path:");
this.pid = this._addDetails("Process ID:"); this.pid = this._addDetails("Process ID:");
this.origin = this._addDetails("Origin:"); this.origin = this._addDetails("Origin IP address:");
this.user = this._addCheckboxDetails("User:"); this.user = this._addCheckboxDetails("User:");
this.group = this._addCheckboxDetails("Group:"); this.group = this._addCheckboxDetails("Group:");
this.sandboxed = sandboxed; this.sandboxed = sandboxed;
if (sandboxed) {
this.sandbox = this._addDetails("Sandbox:");
}
this.optstring = this._addDetails(""); this.optstring = this._addDetails("");
}, },
_addDetails: function(text, d) { _addDetails: function(text, d) {
let title = new St.Label({ style_class: 'fw-detail-title', text: text}); let title = new St.Label({ style_class: 'fw-detail-title', text: text});
//this._left.add(title, { expand: true, x_fill: false, x_align: St.Align.END});
this._left.add(title, { expand: true, x_fill: false, x_align: St.Align.END}); this._left.add(title, { expand: true, x_fill: false, x_align: St.Align.END});
let msg = new St.Label({ style_class: 'fw-detail-message' }); let msg = new St.Label({ style_class: 'fw-detail-message' });
if (d === undefined) { if (d === undefined) {
this._right.add(msg); // this._right.add(msg);
this._right.add(msg, { expand: true, x_fill: false, x_align: St.Align.END});
} else { } else {
let inner = new St.BoxLayout({ vertical: false, style_class: 'fw-ugid-apply-checkbox' }); let inner = new St.BoxLayout({ vertical: false, style_class: 'fw-ugid-apply-checkbox', x_align: St.Align.END });
inner.add(msg); //inner.add(msg);
inner.add(d.actor); inner.add(msg, { expand: true, x_fill: true, x_align: St.Align.END});
inner.add(d.actor, { x_fill: true, x_align: St.Align.END, expand: true});
this._right.add(inner); this._right.add(inner);
} }
return msg; return msg;
@ -60,13 +73,14 @@ const DetailSection = new Lang.Class({
_addCheckboxDetails: function(text) { _addCheckboxDetails: function(text) {
let title = new St.Label({ style_class: 'fw-detail-title', text: text}); let title = new St.Label({ style_class: 'fw-detail-title', text: text});
title.hide(); title.hide();
//this._left.add(title, { expand: true, x_fill: false, x_align: St.Align.END});
this._left.add(title, { expand: true, x_fill: false, x_align: St.Align.END}); this._left.add(title, { expand: true, x_fill: false, x_align: St.Align.END});
//let msg = new St.Label({ style_class: 'fw-detail-message' }); //let msg = new St.Label({ style_class: 'fw-detail-message' });
let check = new CheckBox.CheckBox(""); let check = new CheckBox.CheckBox("");
check.actor.checked = true; check.actor.checked = true;
check.actor.hide(); check.actor.hide();
this._right.add(check.actor); this._right.add(check.actor, { expand: true, x_align: St.Align.END, x_fill: false});
/* /*
let inner = new St.BoxLayout({ vertical: false, style_class: 'fw-ugid-apply-checkbox' }); let inner = new St.BoxLayout({ vertical: false, style_class: 'fw-ugid-apply-checkbox' });
@ -115,10 +129,78 @@ const DetailSection = new Lang.Class({
} }
if (sandbox != "") { if (sandbox != "") {
this.sandbox.text = sandbox;
}
this.optstring.text = optstring //this.sandbox = new St.Label({ style_class: 'fw-detail-message' });
//this._right.remove_child(this.sandbox);
//let yek = new St.Label({ style_class: 'fw-detail-message' });
var [r,g,b] = Misc.pastelColorsFromName(sandbox);
var hexbg = r.toString(16) + g.toString(16) + b.toString(16);
this.sandbox.get_clutter_text().set_markup('<span font_weight="bold" underline_color="#'+hexbg+'"><u>'+sandbox+'</u></span>');
//this._right.add_child(yek);
//this.sandbox.show();
// result_label.get_clutter_text().set_markup('<span foreground="' + styles[stat] + '" underline_color="red">' + Fuzzy.fuzzysort.highlight(r[k], open = '<u>', close = '</u>') + '</span>');
// global.log(hexbg);
/* var _dot = new St.Widget({ style_class: 'realm-running-dot',//'app-well-app-running-dot',
layout_manager: new Clutter.BinLayout(),
x_expand: true, y_expand: true,
x_align: Clutter.ActorAlign.CENTER,
y_align: Clutter.ActorAlign.CENTER });
_dot.style = 'background-color: #'+hexbg+';width: '+width+'px;';
this.sandbox.add_actor(_dot);
this.sandbox = _dot;
_dot.show(); */
}
this.optstring.text = optstring;
let windows = global.get_window_actors();
let tnpid = -1;
let winpids = {};
let t;
let mw;
let x = 0;
let thumb = false;
for (x = 0; x < windows.length; x++) {
mw = windows[x].get_meta_window();
if (typeof mw != 'undefined') {
global.log("pid: "+pid+" mw.get_client_pid(): "+mw.get_client_pid().toString());
winpids[pid] = windows[x].get_meta_window();
if (pid == mw.get_client_pid().toString()) {
t = Misc.getThumbnail(mw);
this._more.add(t);
tnpid = pid;
thumb = true;
break;
}
}
}
if (pid > 1 && tnpid == -1) {
tnpid = Misc.findParentProcessWindow(pid);
global.log(tnpid);
}
if (tnpid > 1 && thumb == false) {
for (x = 0; x < windows.length; x++) {
mw = windows[x].get_meta_window();
if (typeof mw != 'undefined') {
if (tnpid == mw.get_client_pid().toString()) {
t = Misc.getThumbnail(mw);
t.expand = true;
t.x_align = St.Align.END;
t.x_fill = true;
t.y_fill = true;
this._more.add(t);
thumb = true;
break;
}
}
}
}
if (thumb == true) {
this._right.height = this._left.height;
}
} }
}); });
@ -184,7 +266,7 @@ const OptionList = new Lang.Class({
} }
this.actor.add_child(this.buttonGroup.actor); this.actor.add_child(this.buttonGroup.actor);
this.items = []; this.items = [];
this._selected; this._selected = "";
this.tlsGuard = false; this.tlsGuard = false;
if (sandboxed) { if (sandboxed) {
this.tlsGuard = true; this.tlsGuard = true;
@ -595,7 +677,9 @@ const PromptDialogHeader = new Lang.Class({
if (!remaining) { if (!remaining) {
this.waiting.text; this.waiting.text;
} else { } else {
this.waiting.text = "Remaining: " + remaining; //ithis.waiting.text = "Remaining: " + remaining;
// this.waiting = new St.Label({style_class: 'fw-prompt-waiting', text: "Remaining: " + remaining});
} }
}, },
@ -782,7 +866,7 @@ const PromptDialog = new Lang.Class({
} }
if (sandbox != "") { if (sandbox != "") {
application = application + " (sandboxed)" application = application;
} }
this.header.setTitle(application); this.header.setTitle(application);

@ -134,7 +134,7 @@ const FirewallPromptHandler = new Lang.Class({
return false; return false;
} }
let fname = binding.replace(/-([a-z])/g, function (g) { return g[1].toUpperCase(); }); // let fname = binding.replace(/-([a-z])/g, function (g) { return g[1].toUpperCase(); });
let fname = "_on"+ fname[0].toUpperCase() + fname.substr(1); let fname = "_on"+ fname[0].toUpperCase() + fname.substr(1);
if (!( fname in this._dialog )) { if (!( fname in this._dialog )) {
log("SGFW: Invalid key binding (1)... " + fname); log("SGFW: Invalid key binding (1)... " + fname);
@ -291,18 +291,18 @@ const FirewallPromptHandler = new Lang.Class({
} }
}, },
_updateDialogRemainingPrompts: function() { _updateDialogRemainingPrompts: function() { /*
if (this._dialog === null) { if (this._dialog === null) {
return; return;
} }
try { try {
let remaining = (this._guids.length - 1); let remaining = (this._guids.length - 1);
if (remaining > 0) { /*if (remaining > 0) {
this._dialog.updateRemainingPrompts(remaining); this._dialog.updateRemainingPrompts(remaining);
} }
} catch(err) { } catch(err) {
log("SGFW: Error while updating remaining dialogs count: " + err); log("SGFW: Error while updating remaining dialogs count: " + err);
} }*/
return; return;
} }

@ -76,6 +76,10 @@
font-weight: bold; font-weight: bold;
} }
.fw-details-section-container {
padding: 5px;
}
.fw-details-section { .fw-details-section {
padding: 20px; padding: 20px;
} }
@ -113,3 +117,11 @@
padding-top: 2px !important; padding-top: 2px !important;
vertical-align: middle; vertical-align: middle;
} }
.realm-running-dot {
min-width: 15px;
height: 2px;/*3*/
background-color: #ffffff;
padding: 0px 0px 0px 0px;
margin: 0px 0px 0px 0px;
}

@ -269,8 +269,8 @@ func (ds *dbusServer) GetPendingRequests(policy string) (bool, *dbus.Error) {
pc.proto(), pc.proto(),
int32(pc.procInfo().UID), int32(pc.procInfo().UID),
int32(pc.procInfo().GID), int32(pc.procInfo().GID),
uidToUser(pc.procInfo().UID), uidToUser(pc.sandbox(),pc.procInfo().UID),
gidToGroup(pc.procInfo().GID), gidToGroup(pc.sandbox(),pc.procInfo().GID),
int32(pc.procInfo().Pid), int32(pc.procInfo().Pid),
pc.sandbox(), pc.sandbox(),
pc.socks(), pc.socks(),

@ -426,7 +426,7 @@ func (p *Policy) filterPendingOne(rule *Rule, guid string) {
continue continue
} }
if rule.match(pc.src(), pc.dst(), pc.dstPort(), pc.hostname(), pc.proto(), pc.procInfo().UID, pc.procInfo().GID, uidToUser(pc.procInfo().UID), gidToGroup(pc.procInfo().GID), pc.procInfo().Sandbox) { if rule.match(pc.src(), pc.dst(), pc.dstPort(), pc.hostname(), pc.proto(), pc.procInfo().UID, pc.procInfo().GID, uidToUser(pc.sandbox(),pc.procInfo().UID), gidToGroup(pc.sandbox(),pc.procInfo().GID), pc.procInfo().Sandbox) {
prompter := pc.getPrompter() prompter := pc.getPrompter()
if prompter == nil { if prompter == nil {
@ -465,7 +465,7 @@ func (p *Policy) filterPendingOne(rule *Rule, guid string) {
func (p *Policy) filterPending(rule *Rule) { func (p *Policy) filterPending(rule *Rule) {
remaining := []pendingConnection{} remaining := []pendingConnection{}
for _, pc := range p.pendingQueue { for _, pc := range p.pendingQueue {
if rule.match(pc.src(), pc.dst(), pc.dstPort(), pc.hostname(), pc.proto(), pc.procInfo().UID, pc.procInfo().GID, uidToUser(pc.procInfo().UID), gidToGroup(pc.procInfo().GID), pc.procInfo().Sandbox) { if rule.match(pc.src(), pc.dst(), pc.dstPort(), pc.hostname(), pc.proto(), pc.procInfo().UID, pc.procInfo().GID, uidToUser(pc.sandbox(),pc.procInfo().UID), gidToGroup(pc.sandbox(),pc.procInfo().GID), pc.procInfo().Sandbox) {
prompter := pc.getPrompter() prompter := pc.getPrompter()
if prompter == nil { if prompter == nil {
@ -606,7 +606,6 @@ func (fw *Firewall) filterPacket(pkt *nfqueue.NFQPacket, timestamp time.Time) {
// return // return
} else { } else {
ppath = pinfo.ExePath ppath = pinfo.ExePath
optstring = fmt.Sprintf("Realm: %s", pinfo.Realm)
cf := strings.Fields(pinfo.CmdLine) cf := strings.Fields(pinfo.CmdLine)
if len(cf) > 1 && strings.HasPrefix(cf[1], "/") { if len(cf) > 1 && strings.HasPrefix(cf[1], "/") {
for _, intp := range _interpreters { for _, intp := range _interpreters {
@ -896,7 +895,8 @@ func findProcessForPacket(pkt *nfqueue.NFQPacket, reverse bool, strictness int)
} }
if res != nil { if res != nil {
optstr = "Realm: " + OzInitPids[i].Name //optstr = "Realm: " + OzInitPids[i].Name
res.Realm = OzInitPids[i].Name
res.Sandbox = OzInitPids[i].Name res.Sandbox = OzInitPids[i].Name
res.ExePath = GetRealRoot(res.ExePath, OzInitPids[i].Pid) res.ExePath = GetRealRoot(res.ExePath, OzInitPids[i].Pid)
break break

@ -158,7 +158,7 @@ func monitorPromptFDs(pc pendingConnection) {
//fmt.Printf("ADD TO MONITOR: %v | %v / %v / %v\n", pc.policy().application, guid, pid, fd) //fmt.Printf("ADD TO MONITOR: %v | %v / %v / %v\n", pc.policy().application, guid, pid, fd)
if pid == -1 || fd == -1 || prompter == nil { if pid == -1 || fd == -1 || prompter == nil {
log.Warningf("Unexpected error condition occurred while adding socket fd to monitor: %d %d %v",pid, fd, prompter) log.Warning("Unexpected error condition occurred while adding socket fd to monitor");
return return
} else { } else {
log.Warning("No unexpected errors"); log.Warning("No unexpected errors");
@ -315,8 +315,8 @@ func (p *prompter) processConnection(pc pendingConnection) {
pc.proto(), pc.proto(),
int32(pc.procInfo().UID), int32(pc.procInfo().UID),
int32(pc.procInfo().GID), int32(pc.procInfo().GID),
uidToUser(pc.procInfo().UID), uidToUser(pc.sandbox(), pc.procInfo().UID),
gidToGroup(pc.procInfo().GID), gidToGroup(pc.sandbox(), pc.procInfo().GID),
int32(pc.procInfo().Pid), int32(pc.procInfo().Pid),
pc.sandbox(), pc.sandbox(),
pc.socks(), pc.socks(),
@ -589,7 +589,16 @@ func lookupGroup(gid int) string {
return g.Name return g.Name
} }
func uidToUser(uid int) string { func uidToUser(realm string, uid int) string {
// TODO: cache
if (realm != "") {
user := "";
var db,_ = dbus.SystemBus()
obj := db.Object("com.subgraph.realms", "/")
obj.Call("com.subgraph.realms.Manager.RealmUsernameFromUID", 0, realm, strconv.Itoa(uid)).Store(&user)
return user;
}
uname, ok := userMap[uid] uname, ok := userMap[uid]
if ok { if ok {
return uname return uname
@ -599,7 +608,16 @@ func uidToUser(uid int) string {
return uname return uname
} }
func gidToGroup(gid int) string { func gidToGroup(realm string, gid int) string {
// TODO: cache
if (realm != "") {
group := "";
var db,_ = dbus.SystemBus()
obj := db.Object("com.subgraph.realms", "/")
obj.Call("com.subgraph.realms.Manager.RealmGroupnameFromGID", 0, realm, strconv.Itoa(gid)).Store(&group)
return group;
}
gname, ok := groupMap[gid] gname, ok := groupMap[gid]
if ok { if ok {
return gname return gname

@ -200,7 +200,7 @@ func (rl *RuleList) filter(pkt *nfqueue.NFQPacket, src, dst net.IP, dstPort uint
//log.Notice("! Skipping comparison of mismatching PIDs") //log.Notice("! Skipping comparison of mismatching PIDs")
continue continue
} }
if r.match(src, dst, dstPort, hostname, nfqproto, pinfo.UID, pinfo.GID, uidToUser(pinfo.UID), gidToGroup(pinfo.GID), pinfo.Sandbox) { if r.match(src, dst, dstPort, hostname, nfqproto, pinfo.UID, pinfo.GID, uidToUser(pinfo.Sandbox, pinfo.UID), gidToGroup(pinfo.Sandbox, pinfo.GID), pinfo.Sandbox) {
// log.Notice("+ MATCH SUCCEEDED") // log.Notice("+ MATCH SUCCEEDED")
dstStr := dst.String() dstStr := dst.String()
if FirewallConfig.LogRedact { if FirewallConfig.LogRedact {

Loading…
Cancel
Save