Bläddra i källkod

Feature #TASK_QT-18250 增加两个函数地址的查找

rock.wu 9 månader sedan
förälder
incheckning
86f5683623
3 ändrade filer med 81 tillägg och 17 borttagningar
  1. 8 0
      ebpftracer/jvm.go
  2. 2 0
      ebpftracer/tracer/inject/inject.go
  3. 71 17
      ebpftracer/tracer/inject/inject_linux_amd64.go

+ 8 - 0
ebpftracer/jvm.go

@@ -20,6 +20,8 @@ const (
 	// binPath           = "/root/code/jdk8u/build/linux-x86_64-normal-server-release/jdk/lib/amd64/libnio.so"
 	symbolsocketRead0  = "Java_sun_nio_ch_FileDispatcherImpl_read0" // display /s $rsi
 	symbolsocketWrite0 = "Java_java_net_SocketOutputStream_socketWrite0"
+	symbolgetTTL = "Java_java_net_PlainDatagramSocketImpl_getTTL"
+	symbolgetConvert0 = "Java_sun_net_sdp_SdpSupport_convert0"
 )
 
 func (t *Tracer) AttachJavaNioReadUprobes(pid uint32, codeType CodeType, rootfs string) ([]link.Link, error) {
@@ -183,6 +185,12 @@ func (t *Tracer) AttachJavaNetWriteUprobes(pid uint32, rootfs string) ([]link.Li
 			FuncSymbol: inject.InstInfo{
 				SymName: uProbeData.Func,
 			},
+			FuncConvert0Symbol: inject.InstInfo{
+				SymName: symbolgetConvert0,
+			},
+			FuncGetTTLSymbol: inject.InstInfo{
+				SymName: symbolgetTTL,
+			},
 			//ProcLoadPath: procMapsLoadPath,
 		},
 		RecodeInfo: inject.LibNetInfo{FuncSymbol: inject.InstInfo{SymName: "CW_RECODE_" + originFunc}},

+ 2 - 0
ebpftracer/tracer/inject/inject.go

@@ -17,6 +17,8 @@ type LibNetInfo struct {
 	LibName      string
 	LibPath      string
 	FuncSymbol   InstInfo
+	FuncConvert0Symbol   InstInfo
+	FuncGetTTLSymbol   InstInfo
 	InnerSymbol  InnerSymbolInfo
 	ProcLoadPath string
 	FileDeleted  bool

+ 71 - 17
ebpftracer/tracer/inject/inject_linux_amd64.go

@@ -612,6 +612,24 @@ func (j *JvmInjector) findDebugFuncContextFromLibPath() error {
 		return fmt.Errorf("Error getting function offset: %v", err)
 	}
 
+	functionConvert0Sym, err := GetFunctionOffset(j.DebugLibNetInfo.LibPath, j.DebugLibNetInfo.FuncConvert0Symbol.SymName)
+	// 计算函数的实际内存地址
+	j.DebugLibNetInfo.FuncConvert0Symbol.SymAddr = baseAddress + functionConvert0Sym.Value
+	j.DebugLibNetInfo.FuncConvert0Symbol.SymSize = functionConvert0Sym.Size
+
+	if err != nil {
+		return fmt.Errorf("Error getting function offset: %v", err)
+	}
+
+	functionGetTTLSym, err := GetFunctionOffset(j.DebugLibNetInfo.LibPath, j.DebugLibNetInfo.FuncGetTTLSymbol.SymName)
+	// 计算函数的实际内存地址
+	j.DebugLibNetInfo.FuncGetTTLSymbol.SymAddr = baseAddress + functionGetTTLSym.Value
+	j.DebugLibNetInfo.FuncGetTTLSymbol.SymSize = functionGetTTLSym.Size
+
+	if err != nil {
+		return fmt.Errorf("Error getting function offset: %v", err)
+	}
+
 	_, err = j.findDebugAddressInfoFromMem()
 	if err != nil {
 		return fmt.Errorf("Error finding first CALL instuction: %v", err)
@@ -731,6 +749,37 @@ func modifyReleaseFuncEnter(pid int, originEnterAddr, debugEnterAddr uintptr) er
 	return nil
 }
 
+// func modifyReleaseFuncEnter(pid int, originEnterAddr, debugEnterAddr uintptr) error {
+// 	// offset := debugEnterAddr - (originEnterAddr + 5)
+
+// 	// 读取原始数据
+// 	alignedAddr := originEnterAddr & ^(uintptr(unsafe.Sizeof(uintptr(0))) - 1)
+// 	originalData, err := readData(pid, alignedAddr)
+// 	if err != nil {
+// 		return err
+// 	}
+
+// 	bytes := (*[12]byte)(unsafe.Pointer(&originalData))
+// 	bytes[originEnterAddr%uintptr(unsafe.Sizeof(uintptr(0)))] = 0x48
+// 	bytes[originEnterAddr%uintptr(unsafe.Sizeof(uintptr(1)))] = 0xb8
+// 	bytes[originEnterAddr%uintptr(unsafe.Sizeof(uintptr(2)))] = debugEnterAddr
+// 	bytes[originEnterAddr%uintptr(unsafe.Sizeof(uintptr(3)))] = debugEnterAddr >> 1
+// 	bytes[originEnterAddr%uintptr(unsafe.Sizeof(uintptr(4)))] = debugEnterAddr >> 2
+// 	bytes[originEnterAddr%uintptr(unsafe.Sizeof(uintptr(5)))] = debugEnterAddr >> 3
+// 	bytes[originEnterAddr%uintptr(unsafe.Sizeof(uintptr(6)))] = debugEnterAddr >> 4
+// 	bytes[originEnterAddr%uintptr(unsafe.Sizeof(uintptr(7)))] = debugEnterAddr >> 5
+// 	bytes[originEnterAddr%uintptr(unsafe.Sizeof(uintptr(8)))] = debugEnterAddr >> 6
+// 	bytes[originEnterAddr%uintptr(unsafe.Sizeof(uintptr(9)))] = debugEnterAddr >> 7
+// 	bytes[originEnterAddr%uintptr(unsafe.Sizeof(uintptr(10)))] = 0xff
+// 	bytes[originEnterAddr%uintptr(unsafe.Sizeof(uintptr(11)))] = 0xe0
+// 	// *(*uint32)(unsafe.Pointer(&bytes[(originEnterAddr%uintptr(unsafe.Sizeof(uintptr(0))))+1])) = uint32(offset)
+// 	// err = writeData(pid, alignedAddr, originalData)
+// 	// if err != nil {
+// 	// 	return err
+// 	// }
+// 	return nil
+// }
+
 func restoreOriginalInstructions(pid int, addr uintptr, instructions []byte) error {
 	alignedAddr := addr & ^(uintptr(unsafe.Sizeof(uintptr(0))) - 1)
 	originalData, err := readData(pid, alignedAddr)
@@ -850,6 +899,8 @@ func JvmInject(jvmInjector *JvmInjector) error {
 	}
 	// 修改
 	debugFuncEnterAddr := uintptr(jvmInjector.DebugLibNetInfo.FuncSymbol.SymAddr)
+	debugFuncGetTTLEnterAddr := uintptr(jvmInjector.DebugLibNetInfo.FuncGetTTLSymbol.SymAddr)
+	debugFuncConvert0EnterAddr := uintptr(jvmInjector.DebugLibNetInfo.FuncConvert0Symbol.SymAddr)
 	debugIoFdAddr := uintptr(jvmInjector.DebugLibNetInfo.InnerSymbol.IO_fd_fdID.SymAddr)
 	debugNetSendAddr := uintptr(jvmInjector.DebugLibNetInfo.InnerSymbol.NET_Send.SymAddr)
 
@@ -860,6 +911,9 @@ func JvmInject(jvmInjector *JvmInjector) error {
 	fmt.Printf("<0x%x> -> <0x%x>\n", originFuncEnterAddr, debugFuncEnterAddr)
 	fmt.Printf("<0x%x> -> <0x%x>\n", debugIoFdAddr, ioFdReleaseTargetAddr)
 	fmt.Printf("<0x%x> -> <0x%x>\n", debugNetSendAddr, netSendReleaseTargetAddr)
+	fmt.Printf("conver0 -> <0x%x>\n", netSendReleaseTargetAddr)
+	fmt.Printf("getttl -> <0x%x>\n", netSendReleaseTargetAddr)
+	
 
 	// 附加到目标进程
 	klog.Infof("attach")
@@ -910,23 +964,23 @@ func JvmInject(jvmInjector *JvmInjector) error {
 		PtraceDetach(pid)
 		return err
 	}
-	// 校验jmp地址修改正确
-	klog.Infof("checkReleaseFuncSymAfterChange")
-	errReleaseFuncSymAfterChange := jvmInjector.checkReleaseFuncSymAfterChange()
-	if errReleaseFuncSymAfterChange != nil {
-		klog.WithError(errReleaseFuncSymAfterChange).Errorf("[inject] failed checkReleaseFuncSymAfterChange")
-		// 回滚
-		if len(jvmInjector.ReleaseLibNetInfo.FuncSymbol.OriginCode) == 5 {
-			err = restoreOriginalInstructions(pid, originFuncEnterAddr, jvmInjector.ReleaseLibNetInfo.FuncSymbol.OriginCode)
-			if err != nil {
-				klog.WithError(err).Errorf("[inject] failed restoreOriginalInstructions")
-				PtraceDetach(pid)
-				return err
-			}
-		}
-		//PtraceDetach(pid)
-		//return errReleaseFuncSymAfterChange
-	}
+	// 校验jmp地址修改正确 临时注释
+	// klog.Infof("checkReleaseFuncSymAfterChange")
+	// errReleaseFuncSymAfterChange := jvmInjector.checkReleaseFuncSymAfterChange()
+	// if errReleaseFuncSymAfterChange != nil {
+	// 	klog.WithError(errReleaseFuncSymAfterChange).Errorf("[inject] failed checkReleaseFuncSymAfterChange")
+	// 	// 回滚
+	// 	if len(jvmInjector.ReleaseLibNetInfo.FuncSymbol.OriginCode) == 5 {
+	// 		err = restoreOriginalInstructions(pid, originFuncEnterAddr, jvmInjector.ReleaseLibNetInfo.FuncSymbol.OriginCode)
+	// 		if err != nil {
+	// 			klog.WithError(err).Errorf("[inject] failed restoreOriginalInstructions")
+	// 			PtraceDetach(pid)
+	// 			return err
+	// 		}
+	// 	}
+	// 	//PtraceDetach(pid)
+	// 	//return errReleaseFuncSymAfterChange
+	// }
 
 	return PtraceDetach(pid)
 }