1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
|
package cmd
import (
"fmt"
"github.com/FalconOpsLLC/goexec/internal/exec"
"github.com/FalconOpsLLC/goexec/internal/windows"
"github.com/RedTeamPentesting/adauth"
"github.com/spf13/cobra"
scmrexec "github.com/FalconOpsLLC/goexec/internal/exec/scmr"
)
func scmrCmdInit() {
registerRpcFlags(scmrCmd)
scmrCmd.PersistentFlags().StringVarP(&executablePath, "executable-path", "f", "", "Full path to remote Windows executable")
scmrCmd.PersistentFlags().StringVarP(&executableArgs, "args", "a", "", "Arguments to pass to executable")
scmrCmd.PersistentFlags().StringVarP(&scmrName, "service-name", "s", "", "Name of service to create or modify")
scmrCmd.MarkPersistentFlagRequired("executable-path")
scmrCmd.MarkPersistentFlagRequired("service-name")
scmrCmd.AddCommand(scmrChangeCmd)
scmrCreateCmdInit()
scmrCmd.AddCommand(scmrCreateCmd)
scmrChangeCmdInit()
}
func scmrChangeCmdInit() {
scmrChangeCmd.Flags().StringVarP(&scmrDisplayName, "display-name", "n", "", "Display name of service to create")
scmrChangeCmd.Flags().BoolVar(&scmrNoStart, "no-start", false, "Don't start service")
}
func scmrCreateCmdInit() {
scmrCreateCmd.Flags().BoolVar(&scmrNoDelete, "no-delete", false, "Don't delete service after execution")
}
var (
// scmr arguments
scmrName string
scmrDisplayName string
scmrNoDelete bool
scmrNoStart bool
scmrArgs = func(cmd *cobra.Command, args []string) (err error) {
if len(args) != 1 {
return fmt.Errorf("expected exactly 1 positional argument, got %d", len(args))
}
if creds, target, err = authOpts.WithTarget(ctx, "cifs", args[0]); err != nil {
return fmt.Errorf("failed to parse target: %w", err)
}
log.Debug().Str("target", args[0]).Msg("Resolved target")
return nil
}
creds *adauth.Credential
target *adauth.Target
scmrCmd = &cobra.Command{
Use: "scmr",
Short: "Establish execution via SCMR",
Args: cobra.NoArgs,
}
scmrCreateCmd = &cobra.Command{
Use: "create [target]",
Short: "Create & run a new Windows service to gain execution",
Args: scmrArgs,
RunE: func(cmd *cobra.Command, args []string) (err error) {
if scmrNoDelete {
log.Warn().Msg("Service will not be deleted after execution")
}
if scmrDisplayName == "" {
scmrDisplayName = scmrName
log.Warn().Msg("No display name specified, using service name as display name")
}
executor := scmrexec.Module{}
execCfg := &exec.ExecutionConfig{
ExecutablePath: executablePath,
ExecutableArgs: executableArgs,
ExecutionMethod: scmrexec.MethodCreate,
ExecutionMethodConfig: scmrexec.MethodCreateConfig{
NoDelete: scmrNoDelete,
ServiceName: scmrName,
DisplayName: scmrDisplayName,
ServiceType: windows.SERVICE_WIN32_OWN_PROCESS,
StartType: windows.SERVICE_DEMAND_START,
},
}
if err := executor.Exec(log.WithContext(ctx), creds, target, execCfg); err != nil {
log.Fatal().Err(err).Msg("SCMR execution failed")
}
return nil
},
}
scmrChangeCmd = &cobra.Command{
Use: "change [target]",
Short: "Change an existing Windows service to gain execution",
Args: scmrArgs,
Run: func(cmd *cobra.Command, args []string) {
executor := scmrexec.Module{}
execCfg := &exec.ExecutionConfig{
ExecutablePath: executablePath,
ExecutableArgs: executableArgs,
ExecutionMethod: scmrexec.MethodModify,
ExecutionMethodConfig: scmrexec.MethodModifyConfig{
NoStart: scmrNoStart,
ServiceName: scmrName,
},
}
if err := executor.Exec(log.WithContext(ctx), creds, target, execCfg); err != nil {
log.Fatal().Err(err).Msg("SCMR execution failed")
}
},
}
)
|