build, internal/build: integrate NSIS with CI processes

This commit is contained in:
Péter Szilágyi 2016-11-07 13:38:40 +02:00
parent 3c0a8d1a48
commit a6bf8cd9cc
No known key found for this signature in database
GPG key ID: 119A76381CCB7DD2
8 changed files with 106 additions and 43 deletions

View file

@ -1,39 +1,40 @@
os: Visual Studio 2015 os: Visual Studio 2015
# Clone directly into GOPATH. # Clone directly into GOPATH.
clone_folder: c:\gopath\src\github.com\ethereum\go-ethereum clone_folder: C:\gopath\src\github.com\ethereum\go-ethereum
clone_depth: 5 clone_depth: 5
version: "{branch}.{build}" version: "{branch}.{build}"
environment: environment:
global: global:
GOPATH: c:\gopath GOPATH: C:\gopath
CC: gcc.exe CC: gcc.exe
matrix: matrix:
- GETH_ARCH: amd64 - GETH_ARCH: amd64
MSYS2_ARCH: x86_64 MSYS2_ARCH: x86_64
MSYS2_BITS: 64 MSYS2_BITS: 64
MSYSTEM: MINGW64 MSYSTEM: MINGW64
PATH: C:\msys64\mingw64\bin\;%PATH% PATH: C:\msys64\mingw64\bin\;C:\Program Files (x86)\NSIS\;%PATH%
- GETH_ARCH: 386 - GETH_ARCH: 386
MSYS2_ARCH: i686 MSYS2_ARCH: i686
MSYS2_BITS: 32 MSYS2_BITS: 32
MSYSTEM: MINGW32 MSYSTEM: MINGW32
PATH: C:\msys64\mingw32\bin\;%PATH% PATH: C:\msys64\mingw32\bin\;C:\Program Files (x86)\NSIS\;%PATH%
install: install:
- rmdir c:\go /s /q - rmdir C:\go /s /q
- appveyor DownloadFile https://storage.googleapis.com/golang/go1.7.3.windows-amd64.zip - appveyor DownloadFile https://storage.googleapis.com/golang/go1.7.3.windows-amd64.zip
- 7z x go1.7.3.windows-amd64.zip -y -oC:\ > NUL - 7z x go1.7.3.windows-amd64.zip -y -oC:\ > NUL
- go version - go version
- gcc --version - gcc --version
build_script: build_script:
- go run build\\ci.go install -arch %GETH_ARCH% - go run build\ci.go install -arch %GETH_ARCH%
after_build: after_build:
- go run build\\ci.go archive -arch %GETH_ARCH% -type zip -signer WINDOWS_SIGNING_KEY -upload gethstore/builds - go run build\ci.go archive -arch %GETH_ARCH% -type zip -signer WINDOWS_SIGNING_KEY -upload gethstore/builds
- go run build\ci.go nsis -arch %GETH_ARCH% -signer WINDOWS_SIGNING_KEY -upload gethstore/builds
test_script: test_script:
- set GOARCH=%GETH_ARCH% - set GOARCH=%GETH_ARCH%
- set CGO_ENABLED=1 - set CGO_ENABLED=1
- go run build\\ci.go test -vet -coverage - go run build\ci.go test -vet -coverage

View file

@ -432,7 +432,7 @@ func makeWorkdir(wdflag string) string {
if wdflag != "" { if wdflag != "" {
err = os.MkdirAll(wdflag, 0744) err = os.MkdirAll(wdflag, 0744)
} else { } else {
wdflag, err = ioutil.TempDir("", "eth-deb-build-") wdflag, err = ioutil.TempDir("", "geth-build-")
} }
if err != nil { if err != nil {
log.Fatal(err) log.Fatal(err)
@ -562,27 +562,65 @@ func stageDebianSource(tmpdir string, meta debMetadata) (pkgdir string) {
return pkgdir return pkgdir
} }
// Create Windows installer. // Windows installer
func doWindowsInstaller(cmdline []string) { func doWindowsInstaller(cmdline []string) {
// Create binaries that user are embedded in installer. // Parse the flags and make skip installer generation on PRs
// The installer depends on the following packages. var (
cmdline = append(cmdline, "./cmd/geth", "./cmd/bootnode", "./cmd/abigen", "./cmd/disasm", "./cmd/evm", "./cmd/rlpdump") arch = flag.String("arch", runtime.GOARCH, "Architecture for cross build packaging")
doInstall(cmdline) signer = flag.String("signer", "", `Environment variable holding the signing key (e.g. WINDOWS_SIGNING_KEY)`)
upload = flag.String("upload", "", `Destination to upload the archives (usually "gethstore/builds")`)
workdir = flag.String("workdir", "", `Output directory for packages (uses temp dir if unset)`)
)
flag.CommandLine.Parse(cmdline)
*workdir = makeWorkdir(*workdir)
env := build.Env()
maybeSkipArchive(env)
// create NSIS package // Configure and run the NSIS installer maker. This assumes that all the needed
outputFile := "/DOUTPUTFILE=geth-" + makeArchiveBasename() // files have been previously built (don't mix building and packaging to keep
// cross compilation complexity to a minimum).
var (
base = archiveBasename(*arch, env)
version = strings.Split(build.VERSION(), ".")
version := strings.Split(build.VERSION(), ".") majorVersion = "/DMAJORVERSION=" + version[0]
if len(version) != 3 { minorVersion = "/DMINORVERSION=" + version[1]
panic("Expected major.minor.build version string, got " + build.VERSION()) buildId = "/DBUILDVERSION=" + version[2]
buildArch = "/DARCH=" + *arch
)
bundles := []struct {
name string
content []string
}{
{"geth-" + base, gethArchiveFiles},
{"geth-alltools-" + base, allToolsArchiveFiles},
} }
majorVersion := "/DMAJORVERSION=" + version[0] for _, bundle := range bundles {
minorVersion := "/DMINORVERSION=" + version[1] // Run NSIS for this specific bundle
buildId := "/DBUILDVERSION=" + version[2] outputFile := "/DOUTPUTFILE=" + bundle.name
cmd := exec.Command("makensis.exe", outputFile, majorVersion, minorVersion, buildId, `.\build\nsis\geth.nsi`) tools := []string{}
for _, file := range bundle.content {
name := filepath.Base(file)
if name != "geth.exe" && name != "COPYING" {
tools = append(tools, name)
}
build.CopyFile(filepath.Join(*workdir, name), file, 0755)
}
build.Render("build/nsis.geth.nsi", filepath.Join(*workdir, "geth.nsi"), 0644, nil)
build.Render("build/nsis.install.nsh", filepath.Join(*workdir, "install.nsh"), 0644, tools)
build.Render("build/nsis.uninstall.nsh", filepath.Join(*workdir, "uninstall.nsh"), 0644, tools)
build.Render("build/nsis.envvarupdate.nsh", filepath.Join(*workdir, "EnvVarUpdate.nsh"), 0644, nil)
build.MustRun(cmd) build.CopyFile(filepath.Join(*workdir, "SimpleFC.dll"), "build/nsis.simplefc.dll", 0755)
makensis := exec.Command("makensis.exe", outputFile, majorVersion, minorVersion, buildId, buildArch, filepath.Join(*workdir, "geth.nsi"))
build.MustRun(makensis)
if err := archiveUpload(filepath.Join(*workdir, bundle.name+".exe"), *upload, *signer); err != nil {
log.Fatal(err)
}
}
} }
// Cross compilation // Cross compilation

View file

@ -27,7 +27,8 @@ CRCCheck on
!define GROUPNAME "Ethereum" !define GROUPNAME "Ethereum"
!define APPNAME "Geth" !define APPNAME "Geth"
!define DESCRIPTION "Official golang implementation of the Ethereum protocol" !define DESCRIPTION "Official Go implementation of the Ethereum protocol"
!addplugindir .\
# Require admin rights on NT6+ (When UAC is turned on) # Require admin rights on NT6+ (When UAC is turned on)
RequestExecutionLevel admin RequestExecutionLevel admin
@ -49,6 +50,12 @@ function .onInit
# make vars are global for all users since geth is installed global # make vars are global for all users since geth is installed global
setShellVarContext all setShellVarContext all
!insertmacro VerifyUserIsAdmin !insertmacro VerifyUserIsAdmin
${If} ${ARCH} == "amd64"
StrCpy $InstDir "$PROGRAMFILES64\${APPNAME}"
${Else}
StrCpy $InstDir "$PROGRAMFILES32\${APPNAME}"
${Endif}
functionEnd functionEnd
!include install.nsh !include install.nsh

View file

@ -1,6 +1,6 @@
Name "geth ${MAJORVERSION}.${MINORVERSION}.${BUILDVERSION}" # VERSION variables set through command line arguments Name "geth ${MAJORVERSION}.${MINORVERSION}.${BUILDVERSION}" # VERSION variables set through command line arguments
InstallDir "$PROGRAMFILES64\${APPNAME}" InstallDir "$InstDir"
OutFile "../bin/${OUTPUTFILE}.exe" # OUTPUTFILE set through command line arguments OutFile "${OUTPUTFILE}.exe" # OUTPUTFILE set through command line arguments
# Links for "Add/Remove Programs" # Links for "Add/Remove Programs"
!define HELPURL "https://github.com/ethereum/go-ethereum/issues" !define HELPURL "https://github.com/ethereum/go-ethereum/issues"
@ -9,17 +9,17 @@ OutFile "../bin/${OUTPUTFILE}.exe" # OUTPUTFILE set through command line argumen
!define /date NOW "%Y%m%d" !define /date NOW "%Y%m%d"
PageEx license PageEx license
LicenseData ../../COPYING LicenseData COPYING
PageExEnd PageExEnd
# Install geth binary # Install geth binary
Section "Geth" GETH_IDX Section "Geth" GETH_IDX
SetOutPath $INSTDIR SetOutPath $INSTDIR
file ..\bin\geth.exe file geth.exe
# Create start menu launcher # Create start menu launcher
createDirectory "$SMPROGRAMS\${APPNAME}" createDirectory "$SMPROGRAMS\${APPNAME}"
createShortCut "$SMPROGRAMS\${APPNAME}\${APPNAME}.lnk" "$INSTDIR\geth.exe" "--fast" "" createShortCut "$SMPROGRAMS\${APPNAME}\${APPNAME}.lnk" "$INSTDIR\geth.exe" "--fast" "--cache=512"
createShortCut "$SMPROGRAMS\${APPNAME}\Attach.lnk" "$INSTDIR\geth.exe" "attach" "" "" createShortCut "$SMPROGRAMS\${APPNAME}\Attach.lnk" "$INSTDIR\geth.exe" "attach" "" ""
createShortCut "$SMPROGRAMS\${APPNAME}\Uninstall.lnk" "$INSTDIR\uninstall.exe" "" "" "" createShortCut "$SMPROGRAMS\${APPNAME}\Uninstall.lnk" "$INSTDIR\uninstall.exe" "" "" ""
@ -44,11 +44,8 @@ SectionEnd
# Install optional develop tools. # Install optional develop tools.
Section /o "Development tools" DEV_TOOLS_IDX Section /o "Development tools" DEV_TOOLS_IDX
SetOutPath $INSTDIR SetOutPath $INSTDIR
file ..\bin\abigen.exe {{range $}}file {{$}}
file ..\bin\bootnode.exe {{end}}
file ..\bin\disasm.exe
file ..\bin\evm.exe
file ..\bin\rlpdump.exe
SectionEnd SectionEnd
# Return on top of stack the total size (as DWORD) of the selected/installed sections. # Return on top of stack the total size (as DWORD) of the selected/installed sections.

BIN
build/nsis.simplefc.dll Normal file

Binary file not shown.

View file

@ -3,12 +3,9 @@ Section "Uninstall"
setShellVarContext all setShellVarContext all
# Delete (optionally) installed files # Delete (optionally) installed files
{{range $}}Delete $INSTDIR\{{$}}
{{end}}
Delete $INSTDIR\geth.exe Delete $INSTDIR\geth.exe
Delete $INSTDIR\abigen.exe
Delete $INSTDIR\bootnode.exe
Delete $INSTDIR\disasm.exe
Delete $INSTDIR\evm.exe
Delete $INSTDIR\rlpdump.exe
Delete $INSTDIR\uninstall.exe Delete $INSTDIR\uninstall.exe
# Delete install directory # Delete install directory

View file

@ -20,6 +20,7 @@ import (
"bytes" "bytes"
"flag" "flag"
"fmt" "fmt"
"io"
"io/ioutil" "io/ioutil"
"log" "log"
"os" "os"
@ -117,3 +118,25 @@ func render(tpl *template.Template, outputFile string, outputPerm os.FileMode, x
log.Fatal(err) log.Fatal(err)
} }
} }
// CopyFile copies a file.
func CopyFile(dst, src string, mode os.FileMode) {
if err := os.MkdirAll(filepath.Dir(dst), 0755); err != nil {
log.Fatal(err)
}
destFile, err := os.OpenFile(dst, os.O_CREATE|os.O_WRONLY|os.O_TRUNC, mode)
if err != nil {
log.Fatal(err)
}
defer destFile.Close()
srcFile, err := os.Open(src)
if err != nil {
log.Fatal(err)
}
defer srcFile.Close()
if _, err := io.Copy(destFile, srcFile); err != nil {
log.Fatal(err)
}
}