最新消息:雨落星辰是一个专注网站SEO优化、网站SEO诊断、搜索引擎研究、网络营销推广、网站策划运营及站长类的自媒体原创博客

exe - How can I inject user-specific data (like a public key) into a pre-built Go binary without needing Go installed? - Stack O

programmeradmin0浏览0评论

I am working on a Go application that encrypts sensitive files using a public key. The goal of my project is to create a customizable encryption tool that allows users to generate an executable tailored to their needs. The idea is that the user will input their own public key, and the tool will produce a unique executable, which they can then use to securely encrypt their files.

The challenge is that I cannot assume the target machine has Go installed for me to compile the code locally. Additionally, I would like to ensure the solution is portable, meaning the executable should be able to run on any machine without requiring Go setup.

How can I inject a user-specific public key into a pre-built Go binary after it’s been compiled? Or are there better solutions that I could not think of?

I am working on a Go application that encrypts sensitive files using a public key. The goal of my project is to create a customizable encryption tool that allows users to generate an executable tailored to their needs. The idea is that the user will input their own public key, and the tool will produce a unique executable, which they can then use to securely encrypt their files.

The challenge is that I cannot assume the target machine has Go installed for me to compile the code locally. Additionally, I would like to ensure the solution is portable, meaning the executable should be able to run on any machine without requiring Go setup.

How can I inject a user-specific public key into a pre-built Go binary after it’s been compiled? Or are there better solutions that I could not think of?

Share Improve this question asked Feb 1 at 4:28 OnyxOnyx 554 bronze badges 3
  • if you remove the need to compile, you will remove need to inject into pre-build go binary, one solution will be to add a menu to your app startup. one flag will be Generate app and another will be Use public key. when app starts in generate mode, it will generate a script (.sh or .bat) to which starts app with public key flag and its address, when app starts in with public key mode, it will read the public key file and use it as key on it's crypto operations. – hmmftg Commented Feb 1 at 5:37
  • These days you can make docker a requirement, especially since your tool will be used by technical users – Arkadiusz Drabczyk Commented Feb 1 at 11:37
  • Or why can't you simply ask for a public key on the first run and then store it in cache? – Arkadiusz Drabczyk Commented Feb 1 at 22:08
Add a comment  | 

2 Answers 2

Reset to default 1

This is an interesting question and, without manually modifying the compiled code, I'm not sure you can. But, since you asked for alternatives, there are a number of options:

  • An encrypted data file that stores the key (you'll need to secure this)
  • A local data store with encryption (need a data store installed in the app environment somewhere)
  • A cloud key service accessible for each instance (AWS provides this)
  • A K8s key store (if the apps are running in that environment)

You could simply read their public key and store it in a local file or something for use since it is "public" (i.e freely available and known).

EDIT: I thought about this overnight and I'm going to strongly recommend against embedding the key(s?) in the executable. If you just mean the "public" key, then there is no need to hide or obscure it. It can be passed in as an app argument or read from an environment variable or some other accessible data store as it need not be kept secret. If you mean to include the "private" key too, then anyone who gets their hands on a copy of your app could read the key and decode the files (assuming they had access). For the private key, you should use some sort of encrypted storage like a database with encryption built in (don't roll your own) or a key store service as mentioned above. Good luck with your application!

You can use objcopy for this with the --add-section flag, there might be other better ways to do this but this is the first one I thought of. You can parse it by either using the elf.h C API or Go's debug/elf directly if you're only worried about ELF executables or you can use something like BFD (I think there's no Go bindings for this) if you want to support other executable formats. objcopy itself uses BFD so you can use it for all the formats it supports. Here's the debug/elf approach:

package main

import (
    "debug/elf"
    "os"
    "fmt"
    "log"
)

func main() {
    exePath, err := os.Executable()
    if err != nil {
        log.Fatal(err)
    }
    exeFile, err := os.Open(exePath)
    if err != nil {
        log.Fatal(err)
    }
    defer exeFile.Close()
    exeELF, err := elf.NewFile(exeFile)
    if err != nil {
        log.Fatal(err)
    }
    myData := exeELF.Section("my_data")
    if myData == nil {
        log.Fatal("my_data section missing")
    }
    data, err := myData.Data()
    if err != nil {
        log.Fatal(err)
    }
    fmt.Println(string(data)) // "lorem ipsum"
}

compile it and add the section. objcopy takes the section data from a file, I called it "data", it contains "lorem ipsum" and my go binary is "goembed", so I'd do objcopy --add-section my_data=data goembed goembed which will overwrite the goembed binary with a new one but with the new section and when you run the program it prints "lorem ipsum". That section can also be edited with --update-section in a similar way. You could even get rid of the objcopy dependency and just do this section adding/editing yourself in Go.

与本文相关的文章

发布评论

评论列表(0)

  1. 暂无评论