diff options
| -rw-r--r-- | .editorconfig | 3 | ||||
| -rw-r--r-- | install.bat | 2460 |
2 files changed, 1233 insertions, 1230 deletions
diff --git a/.editorconfig b/.editorconfig index c96b4ea7..4a191367 100644 --- a/.editorconfig +++ b/.editorconfig | |||
| @@ -10,3 +10,6 @@ indent_size = 3 | |||
| 10 | 10 | ||
| 11 | [Makefile] | 11 | [Makefile] |
| 12 | indent_style = tab | 12 | indent_style = tab |
| 13 | |||
| 14 | [*.bat] | ||
| 15 | end_of_line = crlf \ No newline at end of file | ||
diff --git a/install.bat b/install.bat index e5d9cce0..36c8575a 100644 --- a/install.bat +++ b/install.bat | |||
| @@ -1,1230 +1,1230 @@ | |||
| 1 | rem=rem --[[--lua | 1 | rem=rem --[[--lua |
| 2 | @setlocal& set luafile="%~f0" & if exist "%~f0.bat" set luafile="%~f0.bat" | 2 | @setlocal& set luafile="%~f0" & if exist "%~f0.bat" set luafile="%~f0.bat" |
| 3 | @win32\lua5.1\bin\lua5.1.exe %luafile% %*& exit /b ]] | 3 | @win32\lua5.1\bin\lua5.1.exe %luafile% %*& exit /b ]] |
| 4 | 4 | ||
| 5 | local vars = {} | 5 | local vars = {} |
| 6 | 6 | ||
| 7 | 7 | ||
| 8 | vars.PREFIX = nil | 8 | vars.PREFIX = nil |
| 9 | vars.VERSION = "3.0" | 9 | vars.VERSION = "3.0" |
| 10 | vars.SYSCONFDIR = nil | 10 | vars.SYSCONFDIR = nil |
| 11 | vars.CONFBACKUPDIR = nil | 11 | vars.CONFBACKUPDIR = nil |
| 12 | vars.SYSCONFFILENAME = nil | 12 | vars.SYSCONFFILENAME = nil |
| 13 | vars.CONFIG_FILE = nil | 13 | vars.CONFIG_FILE = nil |
| 14 | vars.TREE_ROOT = nil | 14 | vars.TREE_ROOT = nil |
| 15 | vars.TREE_BIN = nil | 15 | vars.TREE_BIN = nil |
| 16 | vars.TREE_LMODULE = nil | 16 | vars.TREE_LMODULE = nil |
| 17 | vars.TREE_CMODULE = nil | 17 | vars.TREE_CMODULE = nil |
| 18 | vars.LUA_INTERPRETER = nil | 18 | vars.LUA_INTERPRETER = nil |
| 19 | vars.LUA_PREFIX = nil | 19 | vars.LUA_PREFIX = nil |
| 20 | vars.LUA_BINDIR = nil | 20 | vars.LUA_BINDIR = nil |
| 21 | vars.LUA_INCDIR = nil | 21 | vars.LUA_INCDIR = nil |
| 22 | vars.LUA_LIBDIR = nil | 22 | vars.LUA_LIBDIR = nil |
| 23 | vars.LUA_LIBNAME = nil | 23 | vars.LUA_LIBNAME = nil |
| 24 | vars.LUA_VERSION = "5.1" | 24 | vars.LUA_VERSION = "5.1" |
| 25 | vars.LUA_SHORTV = nil -- "51" | 25 | vars.LUA_SHORTV = nil -- "51" |
| 26 | vars.LUA_RUNTIME = nil | 26 | vars.LUA_RUNTIME = nil |
| 27 | vars.UNAME_M = nil | 27 | vars.UNAME_M = nil |
| 28 | vars.COMPILER_ENV_CMD = nil | 28 | vars.COMPILER_ENV_CMD = nil |
| 29 | vars.MINGW_BIN_PATH = nil | 29 | vars.MINGW_BIN_PATH = nil |
| 30 | vars.MINGW_CC = nil | 30 | vars.MINGW_CC = nil |
| 31 | vars.MINGW_MAKE = nil | 31 | vars.MINGW_MAKE = nil |
| 32 | vars.MINGW_RC = nil | 32 | vars.MINGW_RC = nil |
| 33 | vars.MINGW_LD = nil | 33 | vars.MINGW_LD = nil |
| 34 | vars.MINGW_AR = nil | 34 | vars.MINGW_AR = nil |
| 35 | vars.MINGW_RANLIB = nil | 35 | vars.MINGW_RANLIB = nil |
| 36 | 36 | ||
| 37 | local FORCE = false | 37 | local FORCE = false |
| 38 | local FORCE_CONFIG = false | 38 | local FORCE_CONFIG = false |
| 39 | local INSTALL_LUA = false | 39 | local INSTALL_LUA = false |
| 40 | local USE_MINGW = false | 40 | local USE_MINGW = false |
| 41 | local USE_MSVC_MANUAL = false | 41 | local USE_MSVC_MANUAL = false |
| 42 | local REGISTRY = true | 42 | local REGISTRY = true |
| 43 | local NOADMIN = false | 43 | local NOADMIN = false |
| 44 | local PROMPT = true | 44 | local PROMPT = true |
| 45 | local SELFCONTAINED = false | 45 | local SELFCONTAINED = false |
| 46 | 46 | ||
| 47 | local lua_version_set = false | 47 | local lua_version_set = false |
| 48 | 48 | ||
| 49 | --- | 49 | --- |
| 50 | -- Some helpers | 50 | -- Some helpers |
| 51 | -- | 51 | -- |
| 52 | 52 | ||
| 53 | local pe = assert(loadfile(".\\win32\\pe-parser.lua"))() | 53 | local pe = assert(loadfile(".\\win32\\pe-parser.lua"))() |
| 54 | 54 | ||
| 55 | local function die(message) | 55 | local function die(message) |
| 56 | if message then print(message) end | 56 | if message then print(message) end |
| 57 | print() | 57 | print() |
| 58 | print("Failed installing LuaRocks. Run with /? for help.") | 58 | print("Failed installing LuaRocks. Run with /? for help.") |
| 59 | os.exit(1) | 59 | os.exit(1) |
| 60 | end | 60 | end |
| 61 | 61 | ||
| 62 | local function exec(cmd) | 62 | local function exec(cmd) |
| 63 | --print(cmd) | 63 | --print(cmd) |
| 64 | local status = os.execute("type NUL && "..cmd) | 64 | local status = os.execute("type NUL && "..cmd) |
| 65 | return (status == 0 or status == true) -- compat 5.1/5.2 | 65 | return (status == 0 or status == true) -- compat 5.1/5.2 |
| 66 | end | 66 | end |
| 67 | 67 | ||
| 68 | local function exists(filename) | 68 | local function exists(filename) |
| 69 | local fd, _, code = io.open(filename, "r") | 69 | local fd, _, code = io.open(filename, "r") |
| 70 | if code == 13 then | 70 | if code == 13 then |
| 71 | -- code 13 means "Permission denied" on both Unix and Windows | 71 | -- code 13 means "Permission denied" on both Unix and Windows |
| 72 | -- io.open on folders always fails with code 13 on Windows | 72 | -- io.open on folders always fails with code 13 on Windows |
| 73 | return true | 73 | return true |
| 74 | end | 74 | end |
| 75 | if fd then | 75 | if fd then |
| 76 | fd:close() | 76 | fd:close() |
| 77 | return true | 77 | return true |
| 78 | end | 78 | end |
| 79 | return false | 79 | return false |
| 80 | end | 80 | end |
| 81 | 81 | ||
| 82 | local function mkdir (dir) | 82 | local function mkdir (dir) |
| 83 | return exec([[.\win32\tools\mkdir -p "]]..dir..[[" >NUL]]) | 83 | return exec([[.\win32\tools\mkdir -p "]]..dir..[[" >NUL]]) |
| 84 | end | 84 | end |
| 85 | 85 | ||
| 86 | -- does the current user have admin privileges ( = elevated) | 86 | -- does the current user have admin privileges ( = elevated) |
| 87 | local function permission() | 87 | local function permission() |
| 88 | return exec("net session >NUL 2>&1") -- fails if not admin | 88 | return exec("net session >NUL 2>&1") -- fails if not admin |
| 89 | end | 89 | end |
| 90 | 90 | ||
| 91 | -- rename filename (full path) to backupname (name only), appending number if required | 91 | -- rename filename (full path) to backupname (name only), appending number if required |
| 92 | -- returns the new name (name only) | 92 | -- returns the new name (name only) |
| 93 | local function backup(filename, backupname) | 93 | local function backup(filename, backupname) |
| 94 | local path = filename:match("(.+)%\\.-$").."\\" | 94 | local path = filename:match("(.+)%\\.-$").."\\" |
| 95 | local nname = backupname | 95 | local nname = backupname |
| 96 | local i = 0 | 96 | local i = 0 |
| 97 | while exists(path..nname) do | 97 | while exists(path..nname) do |
| 98 | i = i + 1 | 98 | i = i + 1 |
| 99 | nname = backupname..tostring(i) | 99 | nname = backupname..tostring(i) |
| 100 | end | 100 | end |
| 101 | exec([[REN "]]..filename..[[" "]]..nname..[[" > NUL]]) | 101 | exec([[REN "]]..filename..[[" "]]..nname..[[" > NUL]]) |
| 102 | return nname | 102 | return nname |
| 103 | end | 103 | end |
| 104 | 104 | ||
| 105 | -- interpolate string with values from 'vars' table | 105 | -- interpolate string with values from 'vars' table |
| 106 | local function S (tmpl) | 106 | local function S (tmpl) |
| 107 | return (tmpl:gsub('%$([%a_][%w_]*)', vars)) | 107 | return (tmpl:gsub('%$([%a_][%w_]*)', vars)) |
| 108 | end | 108 | end |
| 109 | 109 | ||
| 110 | local function print_help() | 110 | local function print_help() |
| 111 | print(S[[ | 111 | print(S[[ |
| 112 | Installs LuaRocks. | 112 | Installs LuaRocks. |
| 113 | 113 | ||
| 114 | /P [dir] Where to install LuaRocks. | 114 | /P [dir] Where to install LuaRocks. |
| 115 | Default is %PROGRAMFILES%\LuaRocks | 115 | Default is %PROGRAMFILES%\LuaRocks |
| 116 | 116 | ||
| 117 | Configuring the destinations: | 117 | Configuring the destinations: |
| 118 | /TREE [dir] Root of the local system tree of installed rocks. | 118 | /TREE [dir] Root of the local system tree of installed rocks. |
| 119 | Default is {BIN}\..\ if {BIN} ends with '\bin' | 119 | Default is {BIN}\..\ if {BIN} ends with '\bin' |
| 120 | otherwise it is {BIN}\systree. | 120 | otherwise it is {BIN}\systree. |
| 121 | /SCRIPTS [dir] Where to install commandline scripts installed by | 121 | /SCRIPTS [dir] Where to install commandline scripts installed by |
| 122 | rocks. Default is {TREE}\bin. | 122 | rocks. Default is {TREE}\bin. |
| 123 | /LUAMOD [dir] Where to install Lua modules installed by rocks. | 123 | /LUAMOD [dir] Where to install Lua modules installed by rocks. |
| 124 | Default is {TREE}\share\lua\{LV}. | 124 | Default is {TREE}\share\lua\{LV}. |
| 125 | /CMOD [dir] Where to install c modules installed by rocks. | 125 | /CMOD [dir] Where to install c modules installed by rocks. |
| 126 | Default is {TREE}\lib\lua\{LV}. | 126 | Default is {TREE}\lib\lua\{LV}. |
| 127 | /CONFIG [dir] Location where the config file should be installed. | 127 | /CONFIG [dir] Location where the config file should be installed. |
| 128 | Default is to follow /P option | 128 | Default is to follow /P option |
| 129 | /SELFCONTAINED Creates a self contained installation in a single | 129 | /SELFCONTAINED Creates a self contained installation in a single |
| 130 | directory given by /P. | 130 | directory given by /P. |
| 131 | Sets the /TREE and /CONFIG options to the same | 131 | Sets the /TREE and /CONFIG options to the same |
| 132 | location as /P. And does not load registry info | 132 | location as /P. And does not load registry info |
| 133 | with option /NOREG. The only option NOT self | 133 | with option /NOREG. The only option NOT self |
| 134 | contained is the user rock tree, so don't use that | 134 | contained is the user rock tree, so don't use that |
| 135 | if you create a self contained installation. | 135 | if you create a self contained installation. |
| 136 | 136 | ||
| 137 | Configuring the Lua interpreter: | 137 | Configuring the Lua interpreter: |
| 138 | /LV [version] Lua version to use; either 5.1, 5.2, 5.3, or 5.4. | 138 | /LV [version] Lua version to use; either 5.1, 5.2, 5.3, or 5.4. |
| 139 | Default is auto-detected. | 139 | Default is auto-detected. |
| 140 | /LUA [dir] Location where Lua is installed - e.g. c:\lua\5.1\ | 140 | /LUA [dir] Location where Lua is installed - e.g. c:\lua\5.1\ |
| 141 | If not provided, the installer will search the system | 141 | If not provided, the installer will search the system |
| 142 | path and some default locations for a valid Lua | 142 | path and some default locations for a valid Lua |
| 143 | installation. | 143 | installation. |
| 144 | This is the base directory, the installer will look | 144 | This is the base directory, the installer will look |
| 145 | for subdirectories bin, lib, include. Alternatively | 145 | for subdirectories bin, lib, include. Alternatively |
| 146 | these can be specified explicitly using the /INC, | 146 | these can be specified explicitly using the /INC, |
| 147 | /LIB, and /BIN options. | 147 | /LIB, and /BIN options. |
| 148 | /INC [dir] Location of Lua includes - e.g. c:\lua\5.1\include | 148 | /INC [dir] Location of Lua includes - e.g. c:\lua\5.1\include |
| 149 | If provided overrides sub directory found using /LUA. | 149 | If provided overrides sub directory found using /LUA. |
| 150 | /LIB [dir] Location of Lua libraries (.dll/.lib) - e.g. c:\lua\5.1\lib | 150 | /LIB [dir] Location of Lua libraries (.dll/.lib) - e.g. c:\lua\5.1\lib |
| 151 | If provided overrides sub directory found using /LUA. | 151 | If provided overrides sub directory found using /LUA. |
| 152 | /BIN [dir] Location of Lua executables - e.g. c:\lua\5.1\bin | 152 | /BIN [dir] Location of Lua executables - e.g. c:\lua\5.1\bin |
| 153 | If provided overrides sub directory found using /LUA. | 153 | If provided overrides sub directory found using /LUA. |
| 154 | /L Install LuaRocks' own copy of Lua even if detected, | 154 | /L Install LuaRocks' own copy of Lua even if detected, |
| 155 | this will always be a 5.1 installation. | 155 | this will always be a 5.1 installation. |
| 156 | (/LUA, /INC, /LIB, /BIN cannot be used with /L) | 156 | (/LUA, /INC, /LIB, /BIN cannot be used with /L) |
| 157 | 157 | ||
| 158 | Compiler configuration: | 158 | Compiler configuration: |
| 159 | By default the installer will try to determine the | 159 | By default the installer will try to determine the |
| 160 | Microsoft toolchain to use. And will automatically use | 160 | Microsoft toolchain to use. And will automatically use |
| 161 | a setup command to initialize that toolchain when | 161 | a setup command to initialize that toolchain when |
| 162 | LuaRocks is run. If it cannot find it, it will default | 162 | LuaRocks is run. If it cannot find it, it will default |
| 163 | to the /MSVC switch. | 163 | to the /MSVC switch. |
| 164 | /MSVC Use MS toolchain, without a setup command (tools must | 164 | /MSVC Use MS toolchain, without a setup command (tools must |
| 165 | be in your path) | 165 | be in your path) |
| 166 | /MW Use mingw as build system (tools must be in your path) | 166 | /MW Use mingw as build system (tools must be in your path) |
| 167 | 167 | ||
| 168 | Other options: | 168 | Other options: |
| 169 | /FORCECONFIG Use a single config location. Do not use the | 169 | /FORCECONFIG Use a single config location. Do not use the |
| 170 | LUAROCKS_CONFIG variable or the user's home directory. | 170 | LUAROCKS_CONFIG variable or the user's home directory. |
| 171 | Useful to avoid conflicts when LuaRocks | 171 | Useful to avoid conflicts when LuaRocks |
| 172 | is embedded within an application. | 172 | is embedded within an application. |
| 173 | /F Remove installation directory if it already exists. | 173 | /F Remove installation directory if it already exists. |
| 174 | /NOREG Do not load registry info to register '.rockspec' | 174 | /NOREG Do not load registry info to register '.rockspec' |
| 175 | extension with LuaRocks commands (right-click). | 175 | extension with LuaRocks commands (right-click). |
| 176 | /NOADMIN The installer requires admin privileges. If not | 176 | /NOADMIN The installer requires admin privileges. If not |
| 177 | available it will elevate a new process. Use this | 177 | available it will elevate a new process. Use this |
| 178 | switch to prevent elevation, but make sure the | 178 | switch to prevent elevation, but make sure the |
| 179 | destination paths are all accessible for the current | 179 | destination paths are all accessible for the current |
| 180 | user. | 180 | user. |
| 181 | /Q Do not prompt for confirmation of settings | 181 | /Q Do not prompt for confirmation of settings |
| 182 | 182 | ||
| 183 | ]]) | 183 | ]]) |
| 184 | end | 184 | end |
| 185 | 185 | ||
| 186 | -- *********************************************************** | 186 | -- *********************************************************** |
| 187 | -- Option parser | 187 | -- Option parser |
| 188 | -- *********************************************************** | 188 | -- *********************************************************** |
| 189 | local function parse_options(args) | 189 | local function parse_options(args) |
| 190 | for _, option in ipairs(args) do | 190 | for _, option in ipairs(args) do |
| 191 | local name = option.name:upper() | 191 | local name = option.name:upper() |
| 192 | if name == "/?" then | 192 | if name == "/?" then |
| 193 | print_help() | 193 | print_help() |
| 194 | os.exit(0) | 194 | os.exit(0) |
| 195 | elseif name == "/P" then | 195 | elseif name == "/P" then |
| 196 | vars.PREFIX = option.value | 196 | vars.PREFIX = option.value |
| 197 | elseif name == "/CONFIG" then | 197 | elseif name == "/CONFIG" then |
| 198 | vars.SYSCONFDIR = option.value | 198 | vars.SYSCONFDIR = option.value |
| 199 | elseif name == "/TREE" then | 199 | elseif name == "/TREE" then |
| 200 | vars.TREE_ROOT = option.value | 200 | vars.TREE_ROOT = option.value |
| 201 | elseif name == "/SCRIPTS" then | 201 | elseif name == "/SCRIPTS" then |
| 202 | vars.TREE_BIN = option.value | 202 | vars.TREE_BIN = option.value |
| 203 | elseif name == "/LUAMOD" then | 203 | elseif name == "/LUAMOD" then |
| 204 | vars.TREE_LMODULE = option.value | 204 | vars.TREE_LMODULE = option.value |
| 205 | elseif name == "/CMOD" then | 205 | elseif name == "/CMOD" then |
| 206 | vars.TREE_CMODULE = option.value | 206 | vars.TREE_CMODULE = option.value |
| 207 | elseif name == "/LV" then | 207 | elseif name == "/LV" then |
| 208 | vars.LUA_VERSION = option.value | 208 | vars.LUA_VERSION = option.value |
| 209 | lua_version_set = true | 209 | lua_version_set = true |
| 210 | elseif name == "/L" then | 210 | elseif name == "/L" then |
| 211 | INSTALL_LUA = true | 211 | INSTALL_LUA = true |
| 212 | elseif name == "/MW" then | 212 | elseif name == "/MW" then |
| 213 | USE_MINGW = true | 213 | USE_MINGW = true |
| 214 | elseif name == "/MSVC" then | 214 | elseif name == "/MSVC" then |
| 215 | USE_MSVC_MANUAL = true | 215 | USE_MSVC_MANUAL = true |
| 216 | elseif name == "/LUA" then | 216 | elseif name == "/LUA" then |
| 217 | vars.LUA_PREFIX = option.value | 217 | vars.LUA_PREFIX = option.value |
| 218 | elseif name == "/LIB" then | 218 | elseif name == "/LIB" then |
| 219 | vars.LUA_LIBDIR = option.value | 219 | vars.LUA_LIBDIR = option.value |
| 220 | elseif name == "/INC" then | 220 | elseif name == "/INC" then |
| 221 | vars.LUA_INCDIR = option.value | 221 | vars.LUA_INCDIR = option.value |
| 222 | elseif name == "/BIN" then | 222 | elseif name == "/BIN" then |
| 223 | vars.LUA_BINDIR = option.value | 223 | vars.LUA_BINDIR = option.value |
| 224 | elseif name == "/FORCECONFIG" then | 224 | elseif name == "/FORCECONFIG" then |
| 225 | FORCE_CONFIG = true | 225 | FORCE_CONFIG = true |
| 226 | elseif name == "/F" then | 226 | elseif name == "/F" then |
| 227 | FORCE = true | 227 | FORCE = true |
| 228 | elseif name == "/SELFCONTAINED" then | 228 | elseif name == "/SELFCONTAINED" then |
| 229 | SELFCONTAINED = true | 229 | SELFCONTAINED = true |
| 230 | elseif name == "/NOREG" then | 230 | elseif name == "/NOREG" then |
| 231 | REGISTRY = false | 231 | REGISTRY = false |
| 232 | elseif name == "/NOADMIN" then | 232 | elseif name == "/NOADMIN" then |
| 233 | NOADMIN = true | 233 | NOADMIN = true |
| 234 | elseif name == "/Q" then | 234 | elseif name == "/Q" then |
| 235 | PROMPT = false | 235 | PROMPT = false |
| 236 | else | 236 | else |
| 237 | die("Unrecognized option: " .. name) | 237 | die("Unrecognized option: " .. name) |
| 238 | end | 238 | end |
| 239 | end | 239 | end |
| 240 | end | 240 | end |
| 241 | 241 | ||
| 242 | -- check for combination/required flags | 242 | -- check for combination/required flags |
| 243 | local function check_flags() | 243 | local function check_flags() |
| 244 | if SELFCONTAINED then | 244 | if SELFCONTAINED then |
| 245 | if not vars.PREFIX then | 245 | if not vars.PREFIX then |
| 246 | die("Option /P is required when using /SELFCONTAINED") | 246 | die("Option /P is required when using /SELFCONTAINED") |
| 247 | end | 247 | end |
| 248 | if vars.SYSCONFDIR or vars.TREE_ROOT or vars.TREE_BIN or vars.TREE_LMODULE or vars.TREE_CMODULE then | 248 | if vars.SYSCONFDIR or vars.TREE_ROOT or vars.TREE_BIN or vars.TREE_LMODULE or vars.TREE_CMODULE then |
| 249 | die("Cannot combine /TREE, /SCRIPTS, /LUAMOD, /CMOD, or /CONFIG with /SELFCONTAINED") | 249 | die("Cannot combine /TREE, /SCRIPTS, /LUAMOD, /CMOD, or /CONFIG with /SELFCONTAINED") |
| 250 | end | 250 | end |
| 251 | end | 251 | end |
| 252 | if INSTALL_LUA then | 252 | if INSTALL_LUA then |
| 253 | if vars.LUA_INCDIR or vars.LUA_BINDIR or vars.LUA_LIBDIR or vars.LUA_PREFIX then | 253 | if vars.LUA_INCDIR or vars.LUA_BINDIR or vars.LUA_LIBDIR or vars.LUA_PREFIX then |
| 254 | die("Cannot combine option /L with any of /LUA /BIN /LIB /INC") | 254 | die("Cannot combine option /L with any of /LUA /BIN /LIB /INC") |
| 255 | end | 255 | end |
| 256 | if vars.LUA_VERSION ~= "5.1" then | 256 | if vars.LUA_VERSION ~= "5.1" then |
| 257 | die("Bundled Lua version is 5.1, cannot install "..vars.LUA_VERSION) | 257 | die("Bundled Lua version is 5.1, cannot install "..vars.LUA_VERSION) |
| 258 | end | 258 | end |
| 259 | end | 259 | end |
| 260 | if not vars.LUA_VERSION:match("^5%.[1234]$") then | 260 | if not vars.LUA_VERSION:match("^5%.[1234]$") then |
| 261 | die("Bad argument: /LV must either be 5.1, 5.2, 5.3, or 5.4") | 261 | die("Bad argument: /LV must either be 5.1, 5.2, 5.3, or 5.4") |
| 262 | end | 262 | end |
| 263 | if USE_MSVC_MANUAL and USE_MINGW then | 263 | if USE_MSVC_MANUAL and USE_MINGW then |
| 264 | die("Cannot combine option /MSVC and /MW") | 264 | die("Cannot combine option /MSVC and /MW") |
| 265 | end | 265 | end |
| 266 | end | 266 | end |
| 267 | 267 | ||
| 268 | -- *********************************************************** | 268 | -- *********************************************************** |
| 269 | -- Detect Lua | 269 | -- Detect Lua |
| 270 | -- *********************************************************** | 270 | -- *********************************************************** |
| 271 | local function detect_lua_version(interpreter_path) | 271 | local function detect_lua_version(interpreter_path) |
| 272 | local handler = io.popen(('type NUL && "%s" -e "io.stdout:write(_VERSION)" 2>NUL'):format(interpreter_path), "r") | 272 | local handler = io.popen(('type NUL && "%s" -e "io.stdout:write(_VERSION)" 2>NUL'):format(interpreter_path), "r") |
| 273 | if not handler then | 273 | if not handler then |
| 274 | return nil, "interpreter does not work" | 274 | return nil, "interpreter does not work" |
| 275 | end | 275 | end |
| 276 | local full_version = handler:read("*a") | 276 | local full_version = handler:read("*a") |
| 277 | handler:close() | 277 | handler:close() |
| 278 | 278 | ||
| 279 | local version = full_version:match(" (5%.[1234])$") | 279 | local version = full_version:match(" (5%.[1234])$") |
| 280 | if not version then | 280 | if not version then |
| 281 | return nil, "unknown interpreter version '" .. full_version .. "'" | 281 | return nil, "unknown interpreter version '" .. full_version .. "'" |
| 282 | end | 282 | end |
| 283 | return version | 283 | return version |
| 284 | end | 284 | end |
| 285 | 285 | ||
| 286 | local function look_for_interpreter(directory) | 286 | local function look_for_interpreter(directory) |
| 287 | local names | 287 | local names |
| 288 | if lua_version_set then | 288 | if lua_version_set then |
| 289 | names = {S"lua$LUA_VERSION.exe", S"lua$LUA_SHORTV.exe"} | 289 | names = {S"lua$LUA_VERSION.exe", S"lua$LUA_SHORTV.exe"} |
| 290 | else | 290 | else |
| 291 | names = {"lua5.4.exe", "lua54.exe", "lua5.3.exe", "lua53.exe", "lua5.2.exe", "lua52.exe", "lua5.1.exe", "lua51.exe"} | 291 | names = {"lua5.4.exe", "lua54.exe", "lua5.3.exe", "lua53.exe", "lua5.2.exe", "lua52.exe", "lua5.1.exe", "lua51.exe"} |
| 292 | end | 292 | end |
| 293 | table.insert(names, "lua.exe") | 293 | table.insert(names, "lua.exe") |
| 294 | table.insert(names, "luajit.exe") | 294 | table.insert(names, "luajit.exe") |
| 295 | 295 | ||
| 296 | local directories | 296 | local directories |
| 297 | if vars.LUA_BINDIR then | 297 | if vars.LUA_BINDIR then |
| 298 | -- If LUA_BINDIR is specified, look only in that directory. | 298 | -- If LUA_BINDIR is specified, look only in that directory. |
| 299 | directories = {vars.LUA_BINDIR} | 299 | directories = {vars.LUA_BINDIR} |
| 300 | else | 300 | else |
| 301 | -- Try candidate directory and its `bin` subdirectory. | 301 | -- Try candidate directory and its `bin` subdirectory. |
| 302 | directories = {directory, directory .. "\\bin"} | 302 | directories = {directory, directory .. "\\bin"} |
| 303 | end | 303 | end |
| 304 | 304 | ||
| 305 | for _, dir in ipairs(directories) do | 305 | for _, dir in ipairs(directories) do |
| 306 | for _, name in ipairs(names) do | 306 | for _, name in ipairs(names) do |
| 307 | local full_name = dir .. "\\" .. name | 307 | local full_name = dir .. "\\" .. name |
| 308 | if exists(full_name) then | 308 | if exists(full_name) then |
| 309 | print(" Found " .. name .. ", testing it...") | 309 | print(" Found " .. name .. ", testing it...") |
| 310 | local version, err = detect_lua_version(full_name) | 310 | local version, err = detect_lua_version(full_name) |
| 311 | if not version then | 311 | if not version then |
| 312 | print(" Error: " .. err) | 312 | print(" Error: " .. err) |
| 313 | else | 313 | else |
| 314 | if version ~= vars.LUA_VERSION then | 314 | if version ~= vars.LUA_VERSION then |
| 315 | if lua_version_set then | 315 | if lua_version_set then |
| 316 | die("Version of interpreter clashes with the value of /LV. Please check your configuration.") | 316 | die("Version of interpreter clashes with the value of /LV. Please check your configuration.") |
| 317 | else | 317 | else |
| 318 | vars.LUA_VERSION = version | 318 | vars.LUA_VERSION = version |
| 319 | vars.LUA_SHORTV = version:gsub("%.", "") | 319 | vars.LUA_SHORTV = version:gsub("%.", "") |
| 320 | end | 320 | end |
| 321 | end | 321 | end |
| 322 | 322 | ||
| 323 | vars.LUA_INTERPRETER = name | 323 | vars.LUA_INTERPRETER = name |
| 324 | vars.LUA_BINDIR = dir | 324 | vars.LUA_BINDIR = dir |
| 325 | return true | 325 | return true |
| 326 | end | 326 | end |
| 327 | end | 327 | end |
| 328 | end | 328 | end |
| 329 | end | 329 | end |
| 330 | 330 | ||
| 331 | if vars.LUA_BINDIR then | 331 | if vars.LUA_BINDIR then |
| 332 | die(("Working Lua executable (one of %s) not found in %s"):format(table.concat(names, ", "), vars.LUA_BINDIR)) | 332 | die(("Working Lua executable (one of %s) not found in %s"):format(table.concat(names, ", "), vars.LUA_BINDIR)) |
| 333 | end | 333 | end |
| 334 | return false | 334 | return false |
| 335 | end | 335 | end |
| 336 | 336 | ||
| 337 | local function look_for_link_libraries(directory) | 337 | local function look_for_link_libraries(directory) |
| 338 | -- MinGW does not generate .lib, nor needs it to link, but MSVC does, | 338 | -- MinGW does not generate .lib, nor needs it to link, but MSVC does, |
| 339 | -- so .lib must be listed first to ensure they are found first if present, | 339 | -- so .lib must be listed first to ensure they are found first if present, |
| 340 | -- to prevent MSVC trying to link to a .dll, which won't work. | 340 | -- to prevent MSVC trying to link to a .dll, which won't work. |
| 341 | local names = {S"lua$LUA_VERSION.lib", S"lua$LUA_SHORTV.lib", S"lua$LUA_VERSION.dll", S"lua$LUA_SHORTV.dll", "liblua.dll.a"} | 341 | local names = {S"lua$LUA_VERSION.lib", S"lua$LUA_SHORTV.lib", S"lua$LUA_VERSION.dll", S"lua$LUA_SHORTV.dll", "liblua.dll.a"} |
| 342 | local directories | 342 | local directories |
| 343 | if vars.LUA_LIBDIR then | 343 | if vars.LUA_LIBDIR then |
| 344 | directories = {vars.LUA_LIBDIR} | 344 | directories = {vars.LUA_LIBDIR} |
| 345 | else | 345 | else |
| 346 | directories = {directory, directory .. "\\lib", directory .. "\\bin"} | 346 | directories = {directory, directory .. "\\lib", directory .. "\\bin"} |
| 347 | end | 347 | end |
| 348 | 348 | ||
| 349 | for _, dir in ipairs(directories) do | 349 | for _, dir in ipairs(directories) do |
| 350 | for _, name in ipairs(names) do | 350 | for _, name in ipairs(names) do |
| 351 | local full_name = dir .. "\\" .. name | 351 | local full_name = dir .. "\\" .. name |
| 352 | print(" checking for " .. full_name) | 352 | print(" checking for " .. full_name) |
| 353 | if exists(full_name) then | 353 | if exists(full_name) then |
| 354 | vars.LUA_LIBDIR = dir | 354 | vars.LUA_LIBDIR = dir |
| 355 | vars.LUA_LIBNAME = name | 355 | vars.LUA_LIBNAME = name |
| 356 | print(" Found " .. name) | 356 | print(" Found " .. name) |
| 357 | return true | 357 | return true |
| 358 | end | 358 | end |
| 359 | end | 359 | end |
| 360 | end | 360 | end |
| 361 | 361 | ||
| 362 | if vars.LUA_LIBDIR then | 362 | if vars.LUA_LIBDIR then |
| 363 | die(("Link library (one of %s) not found in %s"):format(table.concat(names, ", "), vars.LUA_LIBDIR)) | 363 | die(("Link library (one of %s) not found in %s"):format(table.concat(names, ", "), vars.LUA_LIBDIR)) |
| 364 | end | 364 | end |
| 365 | return false | 365 | return false |
| 366 | end | 366 | end |
| 367 | 367 | ||
| 368 | local function look_for_headers(directory) | 368 | local function look_for_headers(directory) |
| 369 | local directories | 369 | local directories |
| 370 | if vars.LUA_INCDIR then | 370 | if vars.LUA_INCDIR then |
| 371 | directories = {vars.LUA_INCDIR} | 371 | directories = {vars.LUA_INCDIR} |
| 372 | else | 372 | else |
| 373 | directories = { | 373 | directories = { |
| 374 | directory .. S"\\include\\lua\\$LUA_VERSION", | 374 | directory .. S"\\include\\lua\\$LUA_VERSION", |
| 375 | directory .. S"\\include\\lua$LUA_SHORTV", | 375 | directory .. S"\\include\\lua$LUA_SHORTV", |
| 376 | directory .. S"\\include\\lua$LUA_VERSION", | 376 | directory .. S"\\include\\lua$LUA_VERSION", |
| 377 | directory .. "\\include", | 377 | directory .. "\\include", |
| 378 | directory | 378 | directory |
| 379 | } | 379 | } |
| 380 | end | 380 | end |
| 381 | 381 | ||
| 382 | for _, dir in ipairs(directories) do | 382 | for _, dir in ipairs(directories) do |
| 383 | local full_name = dir .. "\\lua.h" | 383 | local full_name = dir .. "\\lua.h" |
| 384 | print(" checking for " .. full_name) | 384 | print(" checking for " .. full_name) |
| 385 | if exists(full_name) then | 385 | if exists(full_name) then |
| 386 | vars.LUA_INCDIR = dir | 386 | vars.LUA_INCDIR = dir |
| 387 | print(" Found lua.h") | 387 | print(" Found lua.h") |
| 388 | return true | 388 | return true |
| 389 | end | 389 | end |
| 390 | end | 390 | end |
| 391 | 391 | ||
| 392 | if vars.LUA_INCDIR then | 392 | if vars.LUA_INCDIR then |
| 393 | die(S"lua.h not found in $LUA_INCDIR") | 393 | die(S"lua.h not found in $LUA_INCDIR") |
| 394 | end | 394 | end |
| 395 | return false | 395 | return false |
| 396 | end | 396 | end |
| 397 | 397 | ||
| 398 | 398 | ||
| 399 | local function get_runtime() | 399 | local function get_runtime() |
| 400 | local f | 400 | local f |
| 401 | vars.LUA_RUNTIME, f = pe.msvcrt(vars.LUA_BINDIR.."\\"..vars.LUA_INTERPRETER) | 401 | vars.LUA_RUNTIME, f = pe.msvcrt(vars.LUA_BINDIR.."\\"..vars.LUA_INTERPRETER) |
| 402 | if type(vars.LUA_RUNTIME) ~= "string" then | 402 | if type(vars.LUA_RUNTIME) ~= "string" then |
| 403 | -- analysis failed, issue a warning | 403 | -- analysis failed, issue a warning |
| 404 | vars.LUA_RUNTIME = "MSVCR80" | 404 | vars.LUA_RUNTIME = "MSVCR80" |
| 405 | print("*** WARNING ***: could not analyse the runtime used, defaulting to "..vars.LUA_RUNTIME) | 405 | print("*** WARNING ***: could not analyse the runtime used, defaulting to "..vars.LUA_RUNTIME) |
| 406 | else | 406 | else |
| 407 | print(" "..f.." uses "..vars.LUA_RUNTIME..".DLL as runtime") | 407 | print(" "..f.." uses "..vars.LUA_RUNTIME..".DLL as runtime") |
| 408 | end | 408 | end |
| 409 | return true | 409 | return true |
| 410 | end | 410 | end |
| 411 | 411 | ||
| 412 | local function get_architecture() | 412 | local function get_architecture() |
| 413 | -- detect processor arch interpreter was compiled for | 413 | -- detect processor arch interpreter was compiled for |
| 414 | local proc = (pe.parse(vars.LUA_BINDIR.."\\"..vars.LUA_INTERPRETER) or {}).Machine | 414 | local proc = (pe.parse(vars.LUA_BINDIR.."\\"..vars.LUA_INTERPRETER) or {}).Machine |
| 415 | if not proc then | 415 | if not proc then |
| 416 | die("Could not detect processor architecture used in "..vars.LUA_INTERPRETER) | 416 | die("Could not detect processor architecture used in "..vars.LUA_INTERPRETER) |
| 417 | end | 417 | end |
| 418 | print("arch: " .. proc .. " -> " .. pe.const.Machine[proc]) | 418 | print("arch: " .. proc .. " -> " .. pe.const.Machine[proc]) |
| 419 | proc = pe.const.Machine[proc] -- collect name from constant value | 419 | proc = pe.const.Machine[proc] -- collect name from constant value |
| 420 | if proc == "IMAGE_FILE_MACHINE_I386" then | 420 | if proc == "IMAGE_FILE_MACHINE_I386" then |
| 421 | proc = "x86" | 421 | proc = "x86" |
| 422 | elseif proc == "IMAGE_FILE_MACHINE_ARM64" then | 422 | elseif proc == "IMAGE_FILE_MACHINE_ARM64" then |
| 423 | proc = "arm64" | 423 | proc = "arm64" |
| 424 | else | 424 | else |
| 425 | proc = "x86_64" | 425 | proc = "x86_64" |
| 426 | end | 426 | end |
| 427 | return proc | 427 | return proc |
| 428 | end | 428 | end |
| 429 | 429 | ||
| 430 | -- get a string value from windows registry. | 430 | -- get a string value from windows registry. |
| 431 | local function get_registry(key, value) | 431 | local function get_registry(key, value) |
| 432 | local keys = {key} | 432 | local keys = {key} |
| 433 | local key64, replaced = key:gsub("(%u+\\Software\\)", "%1Wow6432Node\\", 1) | 433 | local key64, replaced = key:gsub("(%u+\\Software\\)", "%1Wow6432Node\\", 1) |
| 434 | 434 | ||
| 435 | if replaced == 1 then | 435 | if replaced == 1 then |
| 436 | keys = {key64, key} | 436 | keys = {key64, key} |
| 437 | end | 437 | end |
| 438 | 438 | ||
| 439 | for _, k in ipairs(keys) do | 439 | for _, k in ipairs(keys) do |
| 440 | local h = io.popen('reg query "'..k..'" /v '..value..' 2>NUL') | 440 | local h = io.popen('reg query "'..k..'" /v '..value..' 2>NUL') |
| 441 | local output = h:read("*a") | 441 | local output = h:read("*a") |
| 442 | h:close() | 442 | h:close() |
| 443 | 443 | ||
| 444 | local v = output:match("REG_SZ%s+([^\n]+)") | 444 | local v = output:match("REG_SZ%s+([^\n]+)") |
| 445 | if v then | 445 | if v then |
| 446 | return v | 446 | return v |
| 447 | end | 447 | end |
| 448 | end | 448 | end |
| 449 | return nil | 449 | return nil |
| 450 | end | 450 | end |
| 451 | 451 | ||
| 452 | local function get_visual_studio_directory_from_registry() | 452 | local function get_visual_studio_directory_from_registry() |
| 453 | assert(type(vars.LUA_RUNTIME)=="string", "requires vars.LUA_RUNTIME to be set before calling this function.") | 453 | assert(type(vars.LUA_RUNTIME)=="string", "requires vars.LUA_RUNTIME to be set before calling this function.") |
| 454 | local major, minor = vars.LUA_RUNTIME:match('VCR%u*(%d+)(%d)$') -- MSVCR<x><y> or VCRUNTIME<x><y> | 454 | local major, minor = vars.LUA_RUNTIME:match('VCR%u*(%d+)(%d)$') -- MSVCR<x><y> or VCRUNTIME<x><y> |
| 455 | if not major then | 455 | if not major then |
| 456 | print(S[[ Cannot auto-detect Visual Studio version from $LUA_RUNTIME]]) | 456 | print(S[[ Cannot auto-detect Visual Studio version from $LUA_RUNTIME]]) |
| 457 | return nil | 457 | return nil |
| 458 | end | 458 | end |
| 459 | local keys = { | 459 | local keys = { |
| 460 | "HKLM\\Software\\Microsoft\\VisualStudio\\%d.%d\\Setup\\VC", | 460 | "HKLM\\Software\\Microsoft\\VisualStudio\\%d.%d\\Setup\\VC", |
| 461 | "HKLM\\Software\\Microsoft\\VCExpress\\%d.%d\\Setup\\VS" | 461 | "HKLM\\Software\\Microsoft\\VCExpress\\%d.%d\\Setup\\VS" |
| 462 | } | 462 | } |
| 463 | for _, key in ipairs(keys) do | 463 | for _, key in ipairs(keys) do |
| 464 | local versionedkey = key:format(major, minor) | 464 | local versionedkey = key:format(major, minor) |
| 465 | local vcdir = get_registry(versionedkey, "ProductDir") | 465 | local vcdir = get_registry(versionedkey, "ProductDir") |
| 466 | print(" checking: "..versionedkey) | 466 | print(" checking: "..versionedkey) |
| 467 | if vcdir then | 467 | if vcdir then |
| 468 | print(" Found: "..vcdir) | 468 | print(" Found: "..vcdir) |
| 469 | return vcdir | 469 | return vcdir |
| 470 | end | 470 | end |
| 471 | end | 471 | end |
| 472 | return nil | 472 | return nil |
| 473 | end | 473 | end |
| 474 | 474 | ||
| 475 | local function get_visual_studio_directory_from_vswhere() | 475 | local function get_visual_studio_directory_from_vswhere() |
| 476 | assert(type(vars.LUA_RUNTIME)=="string", "requires vars.LUA_RUNTIME to be set before calling this function.") | 476 | assert(type(vars.LUA_RUNTIME)=="string", "requires vars.LUA_RUNTIME to be set before calling this function.") |
| 477 | local major, minor = vars.LUA_RUNTIME:match('VCR%u*(%d+)(%d)$') | 477 | local major, minor = vars.LUA_RUNTIME:match('VCR%u*(%d+)(%d)$') |
| 478 | if not major then | 478 | if not major then |
| 479 | print(S[[ Cannot auto-detect Visual Studio version from $LUA_RUNTIME]]) | 479 | print(S[[ Cannot auto-detect Visual Studio version from $LUA_RUNTIME]]) |
| 480 | return nil | 480 | return nil |
| 481 | end | 481 | end |
| 482 | if tonumber(major) < 14 then | 482 | if tonumber(major) < 14 then |
| 483 | return nil | 483 | return nil |
| 484 | end | 484 | end |
| 485 | local program_dir = os.getenv('PROGRAMFILES(X86)') | 485 | local program_dir = os.getenv('PROGRAMFILES(X86)') |
| 486 | if not program_dir then | 486 | if not program_dir then |
| 487 | return nil | 487 | return nil |
| 488 | end | 488 | end |
| 489 | local vswhere = program_dir.."\\Microsoft Visual Studio\\Installer\\vswhere.exe" | 489 | local vswhere = program_dir.."\\Microsoft Visual Studio\\Installer\\vswhere.exe" |
| 490 | if not exists(vswhere) then | 490 | if not exists(vswhere) then |
| 491 | return nil | 491 | return nil |
| 492 | end | 492 | end |
| 493 | local f, msg = io.popen('"'..vswhere..'" -products * -property installationPath') | 493 | local f, msg = io.popen('"'..vswhere..'" -products * -property installationPath') |
| 494 | if not f then return nil, "failed to run vswhere: "..msg end | 494 | if not f then return nil, "failed to run vswhere: "..msg end |
| 495 | local vsdir = nil | 495 | local vsdir = nil |
| 496 | while true do | 496 | while true do |
| 497 | local l, err = f:read() | 497 | local l, err = f:read() |
| 498 | if not l then | 498 | if not l then |
| 499 | if err then | 499 | if err then |
| 500 | f:close() | 500 | f:close() |
| 501 | return nil, err | 501 | return nil, err |
| 502 | else | 502 | else |
| 503 | break | 503 | break |
| 504 | end | 504 | end |
| 505 | end | 505 | end |
| 506 | vsdir = l | 506 | vsdir = l |
| 507 | end | 507 | end |
| 508 | f:close() | 508 | f:close() |
| 509 | if not vsdir then | 509 | if not vsdir then |
| 510 | return nil | 510 | return nil |
| 511 | end | 511 | end |
| 512 | print(" Visual Studio 2017 or higher found in: "..vsdir) | 512 | print(" Visual Studio 2017 or higher found in: "..vsdir) |
| 513 | return vsdir | 513 | return vsdir |
| 514 | end | 514 | end |
| 515 | 515 | ||
| 516 | local function get_windows_sdk_directory() | 516 | local function get_windows_sdk_directory() |
| 517 | assert(type(vars.LUA_RUNTIME) == "string", "requires vars.LUA_RUNTIME to be set before calling this function.") | 517 | assert(type(vars.LUA_RUNTIME) == "string", "requires vars.LUA_RUNTIME to be set before calling this function.") |
| 518 | -- Only v7.1 and v6.1 shipped with compilers | 518 | -- Only v7.1 and v6.1 shipped with compilers |
| 519 | -- Other versions requires a separate installation of Visual Studio. | 519 | -- Other versions requires a separate installation of Visual Studio. |
| 520 | -- see https://github.com/luarocks/luarocks/pull/443#issuecomment-152792516 | 520 | -- see https://github.com/luarocks/luarocks/pull/443#issuecomment-152792516 |
| 521 | local wsdks = { | 521 | local wsdks = { |
| 522 | ["MSVCR100"] = "v7.1", -- shipped with Visual Studio 2010 compilers. | 522 | ["MSVCR100"] = "v7.1", -- shipped with Visual Studio 2010 compilers. |
| 523 | ["MSVCR100D"] = "v7.1", -- shipped with Visual Studio 2010 compilers. | 523 | ["MSVCR100D"] = "v7.1", -- shipped with Visual Studio 2010 compilers. |
| 524 | ["MSVCR90"] = "v6.1", -- shipped with Visual Studio 2008 compilers. | 524 | ["MSVCR90"] = "v6.1", -- shipped with Visual Studio 2008 compilers. |
| 525 | ["MSVCR90D"] = "v6.1", -- shipped with Visual Studio 2008 compilers. | 525 | ["MSVCR90D"] = "v6.1", -- shipped with Visual Studio 2008 compilers. |
| 526 | } | 526 | } |
| 527 | local wsdkver = wsdks[vars.LUA_RUNTIME] | 527 | local wsdkver = wsdks[vars.LUA_RUNTIME] |
| 528 | if not wsdkver then | 528 | if not wsdkver then |
| 529 | print(S[[ Cannot auto-detect Windows SDK version from $LUA_RUNTIME]]) | 529 | print(S[[ Cannot auto-detect Windows SDK version from $LUA_RUNTIME]]) |
| 530 | return nil | 530 | return nil |
| 531 | end | 531 | end |
| 532 | 532 | ||
| 533 | local key = "HKLM\\Software\\Microsoft\\Microsoft SDKs\\Windows\\"..wsdkver | 533 | local key = "HKLM\\Software\\Microsoft\\Microsoft SDKs\\Windows\\"..wsdkver |
| 534 | print(" checking: "..key) | 534 | print(" checking: "..key) |
| 535 | local dir = get_registry(key, "InstallationFolder") | 535 | local dir = get_registry(key, "InstallationFolder") |
| 536 | if dir then | 536 | if dir then |
| 537 | print(" Found: "..dir) | 537 | print(" Found: "..dir) |
| 538 | return dir | 538 | return dir |
| 539 | end | 539 | end |
| 540 | print(" No SDK found") | 540 | print(" No SDK found") |
| 541 | return nil | 541 | return nil |
| 542 | end | 542 | end |
| 543 | 543 | ||
| 544 | -- returns the batch command to setup msvc compiler path. | 544 | -- returns the batch command to setup msvc compiler path. |
| 545 | -- or an empty string (eg. "") if not found | 545 | -- or an empty string (eg. "") if not found |
| 546 | local function get_msvc_env_setup_cmd() | 546 | local function get_msvc_env_setup_cmd() |
| 547 | print(S[[Looking for Microsoft toolchain matching runtime $LUA_RUNTIME and architecture $UNAME_M]]) | 547 | print(S[[Looking for Microsoft toolchain matching runtime $LUA_RUNTIME and architecture $UNAME_M]]) |
| 548 | 548 | ||
| 549 | assert(type(vars.UNAME_M) == "string", "requires vars.UNAME_M to be set before calling this function.") | 549 | assert(type(vars.UNAME_M) == "string", "requires vars.UNAME_M to be set before calling this function.") |
| 550 | local x64 = vars.UNAME_M=="x86_64" | 550 | local x64 = vars.UNAME_M=="x86_64" |
| 551 | 551 | ||
| 552 | -- 1. try visual studio command line tools of VS 2017 or higher | 552 | -- 1. try visual studio command line tools of VS 2017 or higher |
| 553 | local vsdir, err = get_visual_studio_directory_from_vswhere() | 553 | local vsdir, err = get_visual_studio_directory_from_vswhere() |
| 554 | if err then | 554 | if err then |
| 555 | print(" Error when finding Visual Studio directory from vswhere: "..err) | 555 | print(" Error when finding Visual Studio directory from vswhere: "..err) |
| 556 | end | 556 | end |
| 557 | if vsdir then | 557 | if vsdir then |
| 558 | local vcvarsall = vsdir .. '\\VC\\Auxiliary\\Build\\vcvarsall.bat' | 558 | local vcvarsall = vsdir .. '\\VC\\Auxiliary\\Build\\vcvarsall.bat' |
| 559 | if exists(vcvarsall) then | 559 | if exists(vcvarsall) then |
| 560 | local vcvarsall_args = { x86 = "", x86_64 = " x64", arm64 = " x86_arm64" } | 560 | local vcvarsall_args = { x86 = "", x86_64 = " x64", arm64 = " x86_arm64" } |
| 561 | assert(vcvarsall_args[vars.UNAME_M], "vars.UNAME_M: only x86, x86_64 and arm64 are supported") | 561 | assert(vcvarsall_args[vars.UNAME_M], "vars.UNAME_M: only x86, x86_64 and arm64 are supported") |
| 562 | return ('call "%s"%s'):format(vcvarsall, vcvarsall_args[vars.UNAME_M]) | 562 | return ('call "%s"%s'):format(vcvarsall, vcvarsall_args[vars.UNAME_M]) |
| 563 | end | 563 | end |
| 564 | end | 564 | end |
| 565 | 565 | ||
| 566 | -- 2. try visual studio command line tools | 566 | -- 2. try visual studio command line tools |
| 567 | local vcdir = get_visual_studio_directory_from_registry() | 567 | local vcdir = get_visual_studio_directory_from_registry() |
| 568 | if vcdir then | 568 | if vcdir then |
| 569 | local vcvars_bats = { | 569 | local vcvars_bats = { |
| 570 | x86 = { | 570 | x86 = { |
| 571 | "bin\\vcvars32.bat", -- prefers native compiler | 571 | "bin\\vcvars32.bat", -- prefers native compiler |
| 572 | "bin\\amd64_x86\\vcvarsamd64_x86.bat"-- then cross compiler | 572 | "bin\\amd64_x86\\vcvarsamd64_x86.bat"-- then cross compiler |
| 573 | }, | 573 | }, |
| 574 | x86_64 = { | 574 | x86_64 = { |
| 575 | "bin\\amd64\\vcvars64.bat", -- prefers native compiler | 575 | "bin\\amd64\\vcvars64.bat", -- prefers native compiler |
| 576 | "bin\\x86_amd64\\vcvarsx86_amd64.bat" -- then cross compiler | 576 | "bin\\x86_amd64\\vcvarsx86_amd64.bat" -- then cross compiler |
| 577 | }, | 577 | }, |
| 578 | arm64 = { | 578 | arm64 = { |
| 579 | "bin\\x86_arm64\\vcvarsx86_arm64.bat" -- need to use cross compiler" | 579 | "bin\\x86_arm64\\vcvarsx86_arm64.bat" -- need to use cross compiler" |
| 580 | } | 580 | } |
| 581 | } | 581 | } |
| 582 | assert(vcvars_bats[vars.UNAME_M], "vars.UNAME_M: only x86, arm64 and x86_64 are supported") | 582 | assert(vcvars_bats[vars.UNAME_M], "vars.UNAME_M: only x86, arm64 and x86_64 are supported") |
| 583 | for _, bat in ipairs(vcvars_bats[vars.UNAME_M]) do | 583 | for _, bat in ipairs(vcvars_bats[vars.UNAME_M]) do |
| 584 | local full_path = vcdir .. bat | 584 | local full_path = vcdir .. bat |
| 585 | if exists(full_path) then | 585 | if exists(full_path) then |
| 586 | return ('call "%s"'):format(full_path) | 586 | return ('call "%s"'):format(full_path) |
| 587 | end | 587 | end |
| 588 | end | 588 | end |
| 589 | 589 | ||
| 590 | -- try vcvarsall.bat in case MS changes the undocumented bat files above. | 590 | -- try vcvarsall.bat in case MS changes the undocumented bat files above. |
| 591 | -- but this way we don't know if specified compiler is installed... | 591 | -- but this way we don't know if specified compiler is installed... |
| 592 | local vcvarsall = vcdir .. 'vcvarsall.bat' | 592 | local vcvarsall = vcdir .. 'vcvarsall.bat' |
| 593 | if exists(vcvarsall) then | 593 | if exists(vcvarsall) then |
| 594 | local vcvarsall_args = { x86 = "", x86_64 = " amd64", arm64 = " x86_arm64" } | 594 | local vcvarsall_args = { x86 = "", x86_64 = " amd64", arm64 = " x86_arm64" } |
| 595 | return ('call "%s"%s'):format(vcvarsall, vcvarsall_args[vars.UNAME_M]) | 595 | return ('call "%s"%s'):format(vcvarsall, vcvarsall_args[vars.UNAME_M]) |
| 596 | end | 596 | end |
| 597 | end | 597 | end |
| 598 | 598 | ||
| 599 | -- 3. try for Windows SDKs command line tools. | 599 | -- 3. try for Windows SDKs command line tools. |
| 600 | local wsdkdir = get_windows_sdk_directory() | 600 | local wsdkdir = get_windows_sdk_directory() |
| 601 | if wsdkdir then | 601 | if wsdkdir then |
| 602 | local setenv = wsdkdir.."Bin\\SetEnv.cmd" | 602 | local setenv = wsdkdir.."Bin\\SetEnv.cmd" |
| 603 | if exists(setenv) then | 603 | if exists(setenv) then |
| 604 | return ('call "%s" /%s'):format(setenv, x64 and "x64" or "x86") | 604 | return ('call "%s" /%s'):format(setenv, x64 and "x64" or "x86") |
| 605 | end | 605 | end |
| 606 | end | 606 | end |
| 607 | 607 | ||
| 608 | -- finally, we can't detect more, just don't setup the msvc compiler in luarocks.bat. | 608 | -- finally, we can't detect more, just don't setup the msvc compiler in luarocks.bat. |
| 609 | return "" | 609 | return "" |
| 610 | end | 610 | end |
| 611 | 611 | ||
| 612 | local function get_possible_lua_directories() | 612 | local function get_possible_lua_directories() |
| 613 | if vars.LUA_PREFIX then | 613 | if vars.LUA_PREFIX then |
| 614 | return {vars.LUA_PREFIX} | 614 | return {vars.LUA_PREFIX} |
| 615 | end | 615 | end |
| 616 | 616 | ||
| 617 | -- No prefix given, so use PATH. | 617 | -- No prefix given, so use PATH. |
| 618 | local path = os.getenv("PATH") or "" | 618 | local path = os.getenv("PATH") or "" |
| 619 | local directories = {} | 619 | local directories = {} |
| 620 | for dir in path:gmatch("[^;]+") do | 620 | for dir in path:gmatch("[^;]+") do |
| 621 | -- Remove trailing backslashes, but not from a drive letter like `C:\`. | 621 | -- Remove trailing backslashes, but not from a drive letter like `C:\`. |
| 622 | dir = dir:gsub("([^:])\\+$", "%1") | 622 | dir = dir:gsub("([^:])\\+$", "%1") |
| 623 | -- Remove trailing `bin` subdirectory, the searcher will check there anyway. | 623 | -- Remove trailing `bin` subdirectory, the searcher will check there anyway. |
| 624 | if dir:upper():match("[:\\]BIN$") then | 624 | if dir:upper():match("[:\\]BIN$") then |
| 625 | dir = dir:sub(1, -5) | 625 | dir = dir:sub(1, -5) |
| 626 | end | 626 | end |
| 627 | table.insert(directories, dir) | 627 | table.insert(directories, dir) |
| 628 | end | 628 | end |
| 629 | -- Finally add some other default paths. | 629 | -- Finally add some other default paths. |
| 630 | table.insert(directories, [[c:\lua5.1.2]]) | 630 | table.insert(directories, [[c:\lua5.1.2]]) |
| 631 | table.insert(directories, [[c:\lua]]) | 631 | table.insert(directories, [[c:\lua]]) |
| 632 | table.insert(directories, [[c:\kepler\1.1]]) | 632 | table.insert(directories, [[c:\kepler\1.1]]) |
| 633 | return directories | 633 | return directories |
| 634 | end | 634 | end |
| 635 | 635 | ||
| 636 | local function look_for_lua_install () | 636 | local function look_for_lua_install () |
| 637 | print("Looking for Lua interpreter") | 637 | print("Looking for Lua interpreter") |
| 638 | if vars.LUA_BINDIR and vars.LUA_LIBDIR and vars.LUA_INCDIR then | 638 | if vars.LUA_BINDIR and vars.LUA_LIBDIR and vars.LUA_INCDIR then |
| 639 | if look_for_interpreter(vars.LUA_BINDIR) and | 639 | if look_for_interpreter(vars.LUA_BINDIR) and |
| 640 | look_for_link_libraries(vars.LUA_LIBDIR) and | 640 | look_for_link_libraries(vars.LUA_LIBDIR) and |
| 641 | look_for_headers(vars.LUA_INCDIR) | 641 | look_for_headers(vars.LUA_INCDIR) |
| 642 | then | 642 | then |
| 643 | if get_runtime() then | 643 | if get_runtime() then |
| 644 | print("Runtime check completed.") | 644 | print("Runtime check completed.") |
| 645 | return true | 645 | return true |
| 646 | end | 646 | end |
| 647 | end | 647 | end |
| 648 | return false | 648 | return false |
| 649 | end | 649 | end |
| 650 | 650 | ||
| 651 | for _, directory in ipairs(get_possible_lua_directories()) do | 651 | for _, directory in ipairs(get_possible_lua_directories()) do |
| 652 | print(" checking " .. directory) | 652 | print(" checking " .. directory) |
| 653 | if exists(directory) then | 653 | if exists(directory) then |
| 654 | if look_for_interpreter(directory) then | 654 | if look_for_interpreter(directory) then |
| 655 | print("Interpreter found, now looking for link libraries...") | 655 | print("Interpreter found, now looking for link libraries...") |
| 656 | if look_for_link_libraries(directory) then | 656 | if look_for_link_libraries(directory) then |
| 657 | print("Link library found, now looking for headers...") | 657 | print("Link library found, now looking for headers...") |
| 658 | if look_for_headers(directory) then | 658 | if look_for_headers(directory) then |
| 659 | print("Headers found, checking runtime to use...") | 659 | print("Headers found, checking runtime to use...") |
| 660 | if get_runtime() then | 660 | if get_runtime() then |
| 661 | print("Runtime check completed.") | 661 | print("Runtime check completed.") |
| 662 | return true | 662 | return true |
| 663 | end | 663 | end |
| 664 | end | 664 | end |
| 665 | end | 665 | end |
| 666 | end | 666 | end |
| 667 | end | 667 | end |
| 668 | end | 668 | end |
| 669 | return false | 669 | return false |
| 670 | end | 670 | end |
| 671 | 671 | ||
| 672 | -- backup config[x.x].lua[.bak] | 672 | -- backup config[x.x].lua[.bak] |
| 673 | local function backup_config_files() | 673 | local function backup_config_files() |
| 674 | local temppath | 674 | local temppath |
| 675 | while not temppath do | 675 | while not temppath do |
| 676 | temppath = os.getenv("temp").."\\LR-config-backup-"..tostring(math.random(10000)) | 676 | temppath = os.getenv("temp").."\\LR-config-backup-"..tostring(math.random(10000)) |
| 677 | if exists(temppath) then temppath = nil end | 677 | if exists(temppath) then temppath = nil end |
| 678 | end | 678 | end |
| 679 | vars.CONFBACKUPDIR = temppath | 679 | vars.CONFBACKUPDIR = temppath |
| 680 | mkdir(vars.CONFBACKUPDIR) | 680 | mkdir(vars.CONFBACKUPDIR) |
| 681 | exec(S[[COPY "$PREFIX\config*.*" "$CONFBACKUPDIR" >NUL]]) | 681 | exec(S[[COPY "$PREFIX\config*.*" "$CONFBACKUPDIR" >NUL]]) |
| 682 | end | 682 | end |
| 683 | 683 | ||
| 684 | -- restore previously backed up config files | 684 | -- restore previously backed up config files |
| 685 | local function restore_config_files() | 685 | local function restore_config_files() |
| 686 | if not vars.CONFBACKUPDIR then return end -- there is no backup to restore | 686 | if not vars.CONFBACKUPDIR then return end -- there is no backup to restore |
| 687 | exec(S[[COPY "$CONFBACKUPDIR\config*.*" "$PREFIX" >NUL]]) | 687 | exec(S[[COPY "$CONFBACKUPDIR\config*.*" "$PREFIX" >NUL]]) |
| 688 | -- cleanup | 688 | -- cleanup |
| 689 | exec(S[[RD /S /Q "$CONFBACKUPDIR"]]) | 689 | exec(S[[RD /S /Q "$CONFBACKUPDIR"]]) |
| 690 | vars.CONFBACKUPDIR = nil | 690 | vars.CONFBACKUPDIR = nil |
| 691 | end | 691 | end |
| 692 | 692 | ||
| 693 | -- Find GCC based toolchain | 693 | -- Find GCC based toolchain |
| 694 | local find_gcc_suite = function() | 694 | local find_gcc_suite = function() |
| 695 | 695 | ||
| 696 | -- read output os-command | 696 | -- read output os-command |
| 697 | local read_output = function(cmd) | 697 | local read_output = function(cmd) |
| 698 | local f = io.popen("type NUL && " .. cmd .. ' 2>NUL') | 698 | local f = io.popen("type NUL && " .. cmd .. ' 2>NUL') |
| 699 | if not f then return nil, "failed to open command: " .. tostring(cmd) end | 699 | if not f then return nil, "failed to open command: " .. tostring(cmd) end |
| 700 | local lines = {} | 700 | local lines = {} |
| 701 | while true do | 701 | while true do |
| 702 | local l = f:read() | 702 | local l = f:read() |
| 703 | if not l then | 703 | if not l then |
| 704 | f:close() | 704 | f:close() |
| 705 | return lines | 705 | return lines |
| 706 | end | 706 | end |
| 707 | table.insert(lines, l) | 707 | table.insert(lines, l) |
| 708 | end | 708 | end |
| 709 | end | 709 | end |
| 710 | 710 | ||
| 711 | -- returns: full filename, path, filename | 711 | -- returns: full filename, path, filename |
| 712 | local find_file = function(mask, path) | 712 | local find_file = function(mask, path) |
| 713 | local cmd | 713 | local cmd |
| 714 | if path then | 714 | if path then |
| 715 | cmd = 'where.exe /R "' .. path .. '" ' .. mask | 715 | cmd = 'where.exe /R "' .. path .. '" ' .. mask |
| 716 | else | 716 | else |
| 717 | cmd = 'where.exe ' .. mask | 717 | cmd = 'where.exe ' .. mask |
| 718 | end | 718 | end |
| 719 | local files, err = read_output(cmd) | 719 | local files, err = read_output(cmd) |
| 720 | if not files or not files[1] then | 720 | if not files or not files[1] then |
| 721 | return nil, "couldn't find '".. mask .. "', " .. (err or "not found") | 721 | return nil, "couldn't find '".. mask .. "', " .. (err or "not found") |
| 722 | end | 722 | end |
| 723 | local path, file = string.match(files[1], "^(.+)%\\([^%\\]+)$") | 723 | local path, file = string.match(files[1], "^(.+)%\\([^%\\]+)$") |
| 724 | return files[1], path, file | 724 | return files[1], path, file |
| 725 | end | 725 | end |
| 726 | 726 | ||
| 727 | local first_one = "*gcc.exe" -- first file we're assuming to point to the compiler suite | 727 | local first_one = "*gcc.exe" -- first file we're assuming to point to the compiler suite |
| 728 | local full, path, filename = find_file(first_one, nil) | 728 | local full, path, filename = find_file(first_one, nil) |
| 729 | if not full then | 729 | if not full then |
| 730 | return nil, path | 730 | return nil, path |
| 731 | end | 731 | end |
| 732 | vars.MINGW_BIN_PATH = path | 732 | vars.MINGW_BIN_PATH = path |
| 733 | 733 | ||
| 734 | local result = { | 734 | local result = { |
| 735 | gcc = full | 735 | gcc = full |
| 736 | } | 736 | } |
| 737 | for i, name in ipairs({"make", "ar", "windres", "ranlib"}) do | 737 | for i, name in ipairs({"make", "ar", "windres", "ranlib"}) do |
| 738 | result[name] = find_file(name..".exe", path) | 738 | result[name] = find_file(name..".exe", path) |
| 739 | if not result[name] then | 739 | if not result[name] then |
| 740 | result[name] = find_file("*"..name.."*.exe", path) | 740 | result[name] = find_file("*"..name.."*.exe", path) |
| 741 | end | 741 | end |
| 742 | end | 742 | end |
| 743 | 743 | ||
| 744 | vars.MINGW_MAKE = (result.make and '[['..result.make..']]') or "nil, -- not found by installer" | 744 | vars.MINGW_MAKE = (result.make and '[['..result.make..']]') or "nil, -- not found by installer" |
| 745 | vars.MINGW_CC = (result.gcc and '[['..result.gcc..']]') or "nil, -- not found by installer" | 745 | vars.MINGW_CC = (result.gcc and '[['..result.gcc..']]') or "nil, -- not found by installer" |
| 746 | vars.MINGW_RC = (result.windres and '[['..result.windres..']]') or "nil, -- not found by installer" | 746 | vars.MINGW_RC = (result.windres and '[['..result.windres..']]') or "nil, -- not found by installer" |
| 747 | vars.MINGW_LD = (result.gcc and '[['..result.gcc..']]') or "nil, -- not found by installer" | 747 | vars.MINGW_LD = (result.gcc and '[['..result.gcc..']]') or "nil, -- not found by installer" |
| 748 | vars.MINGW_AR = (result.ar and '[['..result.ar..']]') or "nil, -- not found by installer" | 748 | vars.MINGW_AR = (result.ar and '[['..result.ar..']]') or "nil, -- not found by installer" |
| 749 | vars.MINGW_RANLIB = (result.ranlib and '[['..result.ranlib..']]') or "nil, -- not found by installer" | 749 | vars.MINGW_RANLIB = (result.ranlib and '[['..result.ranlib..']]') or "nil, -- not found by installer" |
| 750 | return true | 750 | return true |
| 751 | end | 751 | end |
| 752 | 752 | ||
| 753 | -- *********************************************************** | 753 | -- *********************************************************** |
| 754 | -- Installer script start | 754 | -- Installer script start |
| 755 | -- *********************************************************** | 755 | -- *********************************************************** |
| 756 | 756 | ||
| 757 | -- Poor man's command-line parsing | 757 | -- Poor man's command-line parsing |
| 758 | local config = {} | 758 | local config = {} |
| 759 | local with_arg = { -- options followed by an argument, others are flags | 759 | local with_arg = { -- options followed by an argument, others are flags |
| 760 | ["/P"] = true, | 760 | ["/P"] = true, |
| 761 | ["/CONFIG"] = true, | 761 | ["/CONFIG"] = true, |
| 762 | ["/TREE"] = true, | 762 | ["/TREE"] = true, |
| 763 | ["/SCRIPTS"] = true, | 763 | ["/SCRIPTS"] = true, |
| 764 | ["/LUAMOD"] = true, | 764 | ["/LUAMOD"] = true, |
| 765 | ["/CMOD"] = true, | 765 | ["/CMOD"] = true, |
| 766 | ["/LV"] = true, | 766 | ["/LV"] = true, |
| 767 | ["/LUA"] = true, | 767 | ["/LUA"] = true, |
| 768 | ["/INC"] = true, | 768 | ["/INC"] = true, |
| 769 | ["/BIN"] = true, | 769 | ["/BIN"] = true, |
| 770 | ["/LIB"] = true, | 770 | ["/LIB"] = true, |
| 771 | } | 771 | } |
| 772 | -- reconstruct argument values with spaces and double quotes | 772 | -- reconstruct argument values with spaces and double quotes |
| 773 | -- this will be damaged by the batch construction at the start of this file | 773 | -- this will be damaged by the batch construction at the start of this file |
| 774 | local oarg = arg -- retain old table | 774 | local oarg = arg -- retain old table |
| 775 | if #arg > 0 then | 775 | if #arg > 0 then |
| 776 | local farg = table.concat(arg, " ") .. " " | 776 | local farg = table.concat(arg, " ") .. " " |
| 777 | arg = {} | 777 | arg = {} |
| 778 | farg = farg:gsub('%"', "") | 778 | farg = farg:gsub('%"', "") |
| 779 | local i = 0 | 779 | local i = 0 |
| 780 | while #farg>0 do | 780 | while #farg>0 do |
| 781 | i = i + 1 | 781 | i = i + 1 |
| 782 | if (farg:sub(1,1) ~= "/") and ((arg[i-1] or ""):sub(1,1) ~= "/") then | 782 | if (farg:sub(1,1) ~= "/") and ((arg[i-1] or ""):sub(1,1) ~= "/") then |
| 783 | i = i - 1 -- continued previous arg | 783 | i = i - 1 -- continued previous arg |
| 784 | if i == 0 then i = 1 end | 784 | if i == 0 then i = 1 end |
| 785 | end | 785 | end |
| 786 | if arg[i] then | 786 | if arg[i] then |
| 787 | arg[i] = arg[i] .. " " | 787 | arg[i] = arg[i] .. " " |
| 788 | else | 788 | else |
| 789 | arg[i] = "" | 789 | arg[i] = "" |
| 790 | end | 790 | end |
| 791 | local v,r = farg:match("^(.-)%s(.*)$") | 791 | local v,r = farg:match("^(.-)%s(.*)$") |
| 792 | arg[i], farg = arg[i]..v, r | 792 | arg[i], farg = arg[i]..v, r |
| 793 | while farg:sub(1,1) == " " do farg = farg:sub(2,-1) end -- remove prefix spaces | 793 | while farg:sub(1,1) == " " do farg = farg:sub(2,-1) end -- remove prefix spaces |
| 794 | end | 794 | end |
| 795 | end | 795 | end |
| 796 | for k,v in pairs(oarg) do if k < 1 then arg[k] = v end end -- copy 0 and negative indexes | 796 | for k,v in pairs(oarg) do if k < 1 then arg[k] = v end end -- copy 0 and negative indexes |
| 797 | 797 | ||
| 798 | -- build config option table with name and value elements | 798 | -- build config option table with name and value elements |
| 799 | local i = 1 | 799 | local i = 1 |
| 800 | while i <= #arg do | 800 | while i <= #arg do |
| 801 | local opt = arg[i] | 801 | local opt = arg[i] |
| 802 | if with_arg[opt:upper()] then | 802 | if with_arg[opt:upper()] then |
| 803 | local value = arg[i + 1] | 803 | local value = arg[i + 1] |
| 804 | if not value then | 804 | if not value then |
| 805 | die("Missing value for option "..opt) | 805 | die("Missing value for option "..opt) |
| 806 | end | 806 | end |
| 807 | config[#config + 1] = { name = opt, value = value } | 807 | config[#config + 1] = { name = opt, value = value } |
| 808 | i = i + 1 | 808 | i = i + 1 |
| 809 | else | 809 | else |
| 810 | config[#config + 1] = { name = opt } | 810 | config[#config + 1] = { name = opt } |
| 811 | end | 811 | end |
| 812 | i = i + 1 | 812 | i = i + 1 |
| 813 | end | 813 | end |
| 814 | 814 | ||
| 815 | print(S"LuaRocks $VERSION.x installer.\n") | 815 | print(S"LuaRocks $VERSION.x installer.\n") |
| 816 | 816 | ||
| 817 | parse_options(config) | 817 | parse_options(config) |
| 818 | 818 | ||
| 819 | print([[ | 819 | print([[ |
| 820 | 820 | ||
| 821 | ======================== | 821 | ======================== |
| 822 | == Checking system... == | 822 | == Checking system... == |
| 823 | ======================== | 823 | ======================== |
| 824 | 824 | ||
| 825 | ]]) | 825 | ]]) |
| 826 | 826 | ||
| 827 | check_flags() | 827 | check_flags() |
| 828 | 828 | ||
| 829 | if not permission() then | 829 | if not permission() then |
| 830 | if not NOADMIN then | 830 | if not NOADMIN then |
| 831 | -- must elevate the process with admin privileges | 831 | -- must elevate the process with admin privileges |
| 832 | if not exec("PowerShell /? >NUL 2>&1") then | 832 | if not exec("PowerShell /? >NUL 2>&1") then |
| 833 | -- powershell is not available, so error out | 833 | -- powershell is not available, so error out |
| 834 | die("No administrative privileges detected and cannot auto-elevate. Please run with admin privileges or use the /NOADMIN switch") | 834 | die("No administrative privileges detected and cannot auto-elevate. Please run with admin privileges or use the /NOADMIN switch") |
| 835 | end | 835 | end |
| 836 | print("Need admin privileges, now elevating a new process to continue installing...") | 836 | print("Need admin privileges, now elevating a new process to continue installing...") |
| 837 | local runner = os.getenv("TEMP").."\\".."LuaRocks_Installer.bat" | 837 | local runner = os.getenv("TEMP").."\\".."LuaRocks_Installer.bat" |
| 838 | local f = io.open(runner, "w") | 838 | local f = io.open(runner, "w") |
| 839 | f:write("@echo off\n") | 839 | f:write("@echo off\n") |
| 840 | f:write("CHDIR /D "..arg[0]:match("(.+)%\\.-$").."\n") -- return to current dir, elevation changes current path | 840 | f:write("CHDIR /D "..arg[0]:match("(.+)%\\.-$").."\n") -- return to current dir, elevation changes current path |
| 841 | f:write('"'..arg[-1]..'" "'..table.concat(arg, '" "', 0)..'"\n') | 841 | f:write('"'..arg[-1]..'" "'..table.concat(arg, '" "', 0)..'"\n') |
| 842 | f:write("ECHO Press any key to close this window...\n") | 842 | f:write("ECHO Press any key to close this window...\n") |
| 843 | f:write("PAUSE > NUL\n") | 843 | f:write("PAUSE > NUL\n") |
| 844 | f:write('DEL "'..runner..'"') -- temp batch file deletes itself | 844 | f:write('DEL "'..runner..'"') -- temp batch file deletes itself |
| 845 | f:close() | 845 | f:close() |
| 846 | -- run the created temp batch file in elevated mode | 846 | -- run the created temp batch file in elevated mode |
| 847 | exec("PowerShell -Command (New-Object -com 'Shell.Application').ShellExecute('"..runner.."', '', '', 'runas')\n") | 847 | exec("PowerShell -Command (New-Object -com 'Shell.Application').ShellExecute('"..runner.."', '', '', 'runas')\n") |
| 848 | print("Now exiting unprivileged installer") | 848 | print("Now exiting unprivileged installer") |
| 849 | os.exit() -- exit here, the newly created elevated process will do the installing | 849 | os.exit() -- exit here, the newly created elevated process will do the installing |
| 850 | else | 850 | else |
| 851 | print("Attempting to install without admin privileges...") | 851 | print("Attempting to install without admin privileges...") |
| 852 | end | 852 | end |
| 853 | else | 853 | else |
| 854 | print("Admin privileges available for installing") | 854 | print("Admin privileges available for installing") |
| 855 | end | 855 | end |
| 856 | 856 | ||
| 857 | vars.PREFIX = vars.PREFIX or os.getenv("PROGRAMFILES")..[[\LuaRocks]] | 857 | vars.PREFIX = vars.PREFIX or os.getenv("PROGRAMFILES")..[[\LuaRocks]] |
| 858 | vars.BINDIR = vars.PREFIX | 858 | vars.BINDIR = vars.PREFIX |
| 859 | vars.LIBDIR = vars.PREFIX | 859 | vars.LIBDIR = vars.PREFIX |
| 860 | vars.LUADIR = S"$PREFIX\\lua" | 860 | vars.LUADIR = S"$PREFIX\\lua" |
| 861 | vars.INCDIR = S"$PREFIX\\include" | 861 | vars.INCDIR = S"$PREFIX\\include" |
| 862 | vars.LUA_SHORTV = vars.LUA_VERSION:gsub("%.", "") | 862 | vars.LUA_SHORTV = vars.LUA_VERSION:gsub("%.", "") |
| 863 | 863 | ||
| 864 | if INSTALL_LUA then | 864 | if INSTALL_LUA then |
| 865 | vars.LUA_INTERPRETER = "lua5.1" | 865 | vars.LUA_INTERPRETER = "lua5.1" |
| 866 | vars.LUA_BINDIR = vars.BINDIR | 866 | vars.LUA_BINDIR = vars.BINDIR |
| 867 | vars.LUA_LIBDIR = vars.LIBDIR | 867 | vars.LUA_LIBDIR = vars.LIBDIR |
| 868 | vars.LUA_INCDIR = vars.INCDIR | 868 | vars.LUA_INCDIR = vars.INCDIR |
| 869 | vars.LUA_LIBNAME = "lua5.1.lib" | 869 | vars.LUA_LIBNAME = "lua5.1.lib" |
| 870 | vars.LUA_RUNTIME = "MSVCR80" | 870 | vars.LUA_RUNTIME = "MSVCR80" |
| 871 | vars.UNAME_M = "x86" | 871 | vars.UNAME_M = "x86" |
| 872 | else | 872 | else |
| 873 | if not look_for_lua_install() then | 873 | if not look_for_lua_install() then |
| 874 | die("Could not find Lua. See /? for options for specifying the location of Lua, or installing a bundled copy of Lua 5.1.") | 874 | die("Could not find Lua. See /? for options for specifying the location of Lua, or installing a bundled copy of Lua 5.1.") |
| 875 | end | 875 | end |
| 876 | vars.UNAME_M = get_architecture() -- can only do when installation was found | 876 | vars.UNAME_M = get_architecture() -- can only do when installation was found |
| 877 | end | 877 | end |
| 878 | 878 | ||
| 879 | -- check location of system tree | 879 | -- check location of system tree |
| 880 | if not vars.TREE_ROOT then | 880 | if not vars.TREE_ROOT then |
| 881 | -- no system tree location given, so we need to construct a default value | 881 | -- no system tree location given, so we need to construct a default value |
| 882 | if vars.LUA_BINDIR:lower():match([[([\/]+bin[\/]*)$]]) then | 882 | if vars.LUA_BINDIR:lower():match([[([\/]+bin[\/]*)$]]) then |
| 883 | -- lua binary is located in a 'bin' subdirectory, so assume | 883 | -- lua binary is located in a 'bin' subdirectory, so assume |
| 884 | -- default Lua layout and match rocktree on top | 884 | -- default Lua layout and match rocktree on top |
| 885 | vars.TREE_ROOT = vars.LUA_BINDIR:lower():gsub([[[\/]+bin[\/]*$]], [[\]]) | 885 | vars.TREE_ROOT = vars.LUA_BINDIR:lower():gsub([[[\/]+bin[\/]*$]], [[\]]) |
| 886 | else | 886 | else |
| 887 | -- no 'bin', so use a named tree next to the Lua executable | 887 | -- no 'bin', so use a named tree next to the Lua executable |
| 888 | vars.TREE_ROOT = vars.LUA_BINDIR .. [[\systree]] | 888 | vars.TREE_ROOT = vars.LUA_BINDIR .. [[\systree]] |
| 889 | end | 889 | end |
| 890 | end | 890 | end |
| 891 | 891 | ||
| 892 | vars.SYSCONFDIR = vars.SYSCONFDIR or vars.PREFIX | 892 | vars.SYSCONFDIR = vars.SYSCONFDIR or vars.PREFIX |
| 893 | vars.SYSCONFFILENAME = S"config-$LUA_VERSION.lua" | 893 | vars.SYSCONFFILENAME = S"config-$LUA_VERSION.lua" |
| 894 | vars.CONFIG_FILE = vars.SYSCONFDIR.."\\"..vars.SYSCONFFILENAME | 894 | vars.CONFIG_FILE = vars.SYSCONFDIR.."\\"..vars.SYSCONFFILENAME |
| 895 | if SELFCONTAINED then | 895 | if SELFCONTAINED then |
| 896 | vars.SYSCONFDIR = vars.PREFIX | 896 | vars.SYSCONFDIR = vars.PREFIX |
| 897 | vars.TREE_ROOT = vars.PREFIX..[[\systree]] | 897 | vars.TREE_ROOT = vars.PREFIX..[[\systree]] |
| 898 | REGISTRY = false | 898 | REGISTRY = false |
| 899 | end | 899 | end |
| 900 | if USE_MINGW then | 900 | if USE_MINGW then |
| 901 | vars.COMPILER_ENV_CMD = "" | 901 | vars.COMPILER_ENV_CMD = "" |
| 902 | local found, err = find_gcc_suite() | 902 | local found, err = find_gcc_suite() |
| 903 | if not found then | 903 | if not found then |
| 904 | die("Failed to find MinGW/gcc based toolchain, make sure it is in your path: " .. tostring(err)) | 904 | die("Failed to find MinGW/gcc based toolchain, make sure it is in your path: " .. tostring(err)) |
| 905 | end | 905 | end |
| 906 | else | 906 | else |
| 907 | vars.COMPILER_ENV_CMD = (USE_MSVC_MANUAL and "") or get_msvc_env_setup_cmd() | 907 | vars.COMPILER_ENV_CMD = (USE_MSVC_MANUAL and "") or get_msvc_env_setup_cmd() |
| 908 | end | 908 | end |
| 909 | 909 | ||
| 910 | print(S[[ | 910 | print(S[[ |
| 911 | 911 | ||
| 912 | ========================== | 912 | ========================== |
| 913 | == System check results == | 913 | == System check results == |
| 914 | ========================== | 914 | ========================== |
| 915 | 915 | ||
| 916 | Will configure LuaRocks with the following paths: | 916 | Will configure LuaRocks with the following paths: |
| 917 | LuaRocks : $PREFIX | 917 | LuaRocks : $PREFIX |
| 918 | Config file : $CONFIG_FILE | 918 | Config file : $CONFIG_FILE |
| 919 | Rocktree : $TREE_ROOT | 919 | Rocktree : $TREE_ROOT |
| 920 | 920 | ||
| 921 | Lua interpreter : $LUA_BINDIR\$LUA_INTERPRETER | 921 | Lua interpreter : $LUA_BINDIR\$LUA_INTERPRETER |
| 922 | binaries : $LUA_BINDIR | 922 | binaries : $LUA_BINDIR |
| 923 | libraries : $LUA_LIBDIR | 923 | libraries : $LUA_LIBDIR |
| 924 | includes : $LUA_INCDIR | 924 | includes : $LUA_INCDIR |
| 925 | architecture: $UNAME_M | 925 | architecture: $UNAME_M |
| 926 | binary link : $LUA_LIBNAME with runtime $LUA_RUNTIME.dll | 926 | binary link : $LUA_LIBNAME with runtime $LUA_RUNTIME.dll |
| 927 | ]]) | 927 | ]]) |
| 928 | 928 | ||
| 929 | if USE_MINGW then | 929 | if USE_MINGW then |
| 930 | print(S[[Compiler : MinGW/gcc (make sure it is in your path before using LuaRocks)]]) | 930 | print(S[[Compiler : MinGW/gcc (make sure it is in your path before using LuaRocks)]]) |
| 931 | print(S[[ in: $MINGW_BIN_PATH]]) | 931 | print(S[[ in: $MINGW_BIN_PATH]]) |
| 932 | else | 932 | else |
| 933 | if vars.COMPILER_ENV_CMD == "" then | 933 | if vars.COMPILER_ENV_CMD == "" then |
| 934 | print("Compiler : Microsoft (make sure it is in your path before using LuaRocks)") | 934 | print("Compiler : Microsoft (make sure it is in your path before using LuaRocks)") |
| 935 | else | 935 | else |
| 936 | print(S[[Compiler : Microsoft, using; $COMPILER_ENV_CMD]]) | 936 | print(S[[Compiler : Microsoft, using; $COMPILER_ENV_CMD]]) |
| 937 | end | 937 | end |
| 938 | end | 938 | end |
| 939 | 939 | ||
| 940 | if PROMPT then | 940 | if PROMPT then |
| 941 | print("\nPress <ENTER> to start installing, or press <CTRL>+<C> to abort. Use install /? for installation options.") | 941 | print("\nPress <ENTER> to start installing, or press <CTRL>+<C> to abort. Use install /? for installation options.") |
| 942 | io.read() | 942 | io.read() |
| 943 | end | 943 | end |
| 944 | 944 | ||
| 945 | print([[ | 945 | print([[ |
| 946 | 946 | ||
| 947 | ============================ | 947 | ============================ |
| 948 | == Installing LuaRocks... == | 948 | == Installing LuaRocks... == |
| 949 | ============================ | 949 | ============================ |
| 950 | 950 | ||
| 951 | ]]) | 951 | ]]) |
| 952 | 952 | ||
| 953 | -- *********************************************************** | 953 | -- *********************************************************** |
| 954 | -- Install LuaRocks files | 954 | -- Install LuaRocks files |
| 955 | -- *********************************************************** | 955 | -- *********************************************************** |
| 956 | 956 | ||
| 957 | if exists(vars.PREFIX) then | 957 | if exists(vars.PREFIX) then |
| 958 | if not FORCE then | 958 | if not FORCE then |
| 959 | die(S"$PREFIX exists. Use /F to force removal and reinstallation.") | 959 | die(S"$PREFIX exists. Use /F to force removal and reinstallation.") |
| 960 | else | 960 | else |
| 961 | backup_config_files() | 961 | backup_config_files() |
| 962 | print(S"Removing $PREFIX...") | 962 | print(S"Removing $PREFIX...") |
| 963 | exec(S[[RD /S /Q "$PREFIX"]]) | 963 | exec(S[[RD /S /Q "$PREFIX"]]) |
| 964 | print() | 964 | print() |
| 965 | end | 965 | end |
| 966 | end | 966 | end |
| 967 | 967 | ||
| 968 | print(S"Installing LuaRocks in $PREFIX...") | 968 | print(S"Installing LuaRocks in $PREFIX...") |
| 969 | if not exists(vars.BINDIR) then | 969 | if not exists(vars.BINDIR) then |
| 970 | if not mkdir(vars.BINDIR) then | 970 | if not mkdir(vars.BINDIR) then |
| 971 | die() | 971 | die() |
| 972 | end | 972 | end |
| 973 | end | 973 | end |
| 974 | 974 | ||
| 975 | if INSTALL_LUA then | 975 | if INSTALL_LUA then |
| 976 | -- Copy the included Lua interpreter binaries | 976 | -- Copy the included Lua interpreter binaries |
| 977 | if not exists(vars.LUA_BINDIR) then | 977 | if not exists(vars.LUA_BINDIR) then |
| 978 | mkdir(vars.LUA_BINDIR) | 978 | mkdir(vars.LUA_BINDIR) |
| 979 | end | 979 | end |
| 980 | if not exists(vars.LUA_INCDIR) then | 980 | if not exists(vars.LUA_INCDIR) then |
| 981 | mkdir(vars.LUA_INCDIR) | 981 | mkdir(vars.LUA_INCDIR) |
| 982 | end | 982 | end |
| 983 | exec(S[[COPY win32\lua5.1\bin\*.* "$LUA_BINDIR" >NUL]]) | 983 | exec(S[[COPY win32\lua5.1\bin\*.* "$LUA_BINDIR" >NUL]]) |
| 984 | exec(S[[COPY win32\lua5.1\include\*.* "$LUA_INCDIR" >NUL]]) | 984 | exec(S[[COPY win32\lua5.1\include\*.* "$LUA_INCDIR" >NUL]]) |
| 985 | print(S"Installed the LuaRocks bundled Lua interpreter in $LUA_BINDIR") | 985 | print(S"Installed the LuaRocks bundled Lua interpreter in $LUA_BINDIR") |
| 986 | end | 986 | end |
| 987 | 987 | ||
| 988 | -- Copy the LuaRocks binaries | 988 | -- Copy the LuaRocks binaries |
| 989 | if not exists(S[[$BINDIR\tools]]) then | 989 | if not exists(S[[$BINDIR\tools]]) then |
| 990 | if not mkdir(S[[$BINDIR\tools]]) then | 990 | if not mkdir(S[[$BINDIR\tools]]) then |
| 991 | die() | 991 | die() |
| 992 | end | 992 | end |
| 993 | end | 993 | end |
| 994 | if not exec(S[[COPY win32\tools\*.* "$BINDIR\tools" >NUL]]) then | 994 | if not exec(S[[COPY win32\tools\*.* "$BINDIR\tools" >NUL]]) then |
| 995 | die() | 995 | die() |
| 996 | end | 996 | end |
| 997 | -- Copy LR bin helper files | 997 | -- Copy LR bin helper files |
| 998 | if not exec(S[[COPY win32\*.* "$BINDIR" >NUL]]) then | 998 | if not exec(S[[COPY win32\*.* "$BINDIR" >NUL]]) then |
| 999 | die() | 999 | die() |
| 1000 | end | 1000 | end |
| 1001 | -- Copy the LuaRocks lua source files | 1001 | -- Copy the LuaRocks lua source files |
| 1002 | if not exists(S[[$LUADIR\luarocks]]) then | 1002 | if not exists(S[[$LUADIR\luarocks]]) then |
| 1003 | if not mkdir(S[[$LUADIR\luarocks]]) then | 1003 | if not mkdir(S[[$LUADIR\luarocks]]) then |
| 1004 | die() | 1004 | die() |
| 1005 | end | 1005 | end |
| 1006 | end | 1006 | end |
| 1007 | if not exec(S[[XCOPY /S src\luarocks\*.* "$LUADIR\luarocks" >NUL]]) then | 1007 | if not exec(S[[XCOPY /S src\luarocks\*.* "$LUADIR\luarocks" >NUL]]) then |
| 1008 | die() | 1008 | die() |
| 1009 | end | 1009 | end |
| 1010 | -- Create start scripts | 1010 | -- Create start scripts |
| 1011 | if not exec(S[[COPY src\bin\*.* "$BINDIR" >NUL]]) then | 1011 | if not exec(S[[COPY src\bin\*.* "$BINDIR" >NUL]]) then |
| 1012 | die() | 1012 | die() |
| 1013 | end | 1013 | end |
| 1014 | for _, c in ipairs{"luarocks", "luarocks-admin"} do | 1014 | for _, c in ipairs{"luarocks", "luarocks-admin"} do |
| 1015 | -- rename unix-lua scripts to .lua files | 1015 | -- rename unix-lua scripts to .lua files |
| 1016 | if not exec( (S[[RENAME "$BINDIR\%s" %s.lua]]):format(c, c) ) then | 1016 | if not exec( (S[[RENAME "$BINDIR\%s" %s.lua]]):format(c, c) ) then |
| 1017 | die() | 1017 | die() |
| 1018 | end | 1018 | end |
| 1019 | -- create a bootstrap batch file for the lua file, to start them | 1019 | -- create a bootstrap batch file for the lua file, to start them |
| 1020 | exec(S[[DEL /F /Q "$BINDIR\]]..c..[[.bat" 2>NUL]]) | 1020 | exec(S[[DEL /F /Q "$BINDIR\]]..c..[[.bat" 2>NUL]]) |
| 1021 | local f = io.open(vars.BINDIR.."\\"..c..".bat", "w") | 1021 | local f = io.open(vars.BINDIR.."\\"..c..".bat", "w") |
| 1022 | f:write(S[[ | 1022 | f:write(S[[ |
| 1023 | @ECHO OFF | 1023 | @ECHO OFF |
| 1024 | SETLOCAL ENABLEDELAYEDEXPANSION ENABLEEXTENSIONS | 1024 | SETLOCAL ENABLEDELAYEDEXPANSION ENABLEEXTENSIONS |
| 1025 | $COMPILER_ENV_CMD >NUL | 1025 | $COMPILER_ENV_CMD >NUL |
| 1026 | SET "LUA_PATH=$LUADIR\?.lua;$LUADIR\?\init.lua;%LUA_PATH%" | 1026 | SET "LUA_PATH=$LUADIR\?.lua;$LUADIR\?\init.lua;%LUA_PATH%" |
| 1027 | IF NOT "%LUA_PATH_5_2%"=="" ( | 1027 | IF NOT "%LUA_PATH_5_2%"=="" ( |
| 1028 | SET "LUA_PATH_5_2=$LUADIR\?.lua;$LUADIR\?\init.lua;%LUA_PATH_5_2%" | 1028 | SET "LUA_PATH_5_2=$LUADIR\?.lua;$LUADIR\?\init.lua;%LUA_PATH_5_2%" |
| 1029 | ) | 1029 | ) |
| 1030 | IF NOT "%LUA_PATH_5_3%"=="" ( | 1030 | IF NOT "%LUA_PATH_5_3%"=="" ( |
| 1031 | SET "LUA_PATH_5_3=$LUADIR\?.lua;$LUADIR\?\init.lua;%LUA_PATH_5_3%" | 1031 | SET "LUA_PATH_5_3=$LUADIR\?.lua;$LUADIR\?\init.lua;%LUA_PATH_5_3%" |
| 1032 | ) | 1032 | ) |
| 1033 | SET "PATH=$BINDIR;%PATH%" | 1033 | SET "PATH=$BINDIR;%PATH%" |
| 1034 | "$LUA_BINDIR\$LUA_INTERPRETER" "$BINDIR\]]..c..[[.lua" %* | 1034 | "$LUA_BINDIR\$LUA_INTERPRETER" "$BINDIR\]]..c..[[.lua" %* |
| 1035 | SET EXITCODE=%ERRORLEVEL% | 1035 | SET EXITCODE=%ERRORLEVEL% |
| 1036 | IF NOT "%EXITCODE%"=="2" GOTO EXITLR | 1036 | IF NOT "%EXITCODE%"=="2" GOTO EXITLR |
| 1037 | 1037 | ||
| 1038 | REM Permission denied error, try and auto elevate... | 1038 | REM Permission denied error, try and auto elevate... |
| 1039 | REM already an admin? (checking to prevent loops) | 1039 | REM already an admin? (checking to prevent loops) |
| 1040 | NET SESSION >NUL 2>&1 | 1040 | NET SESSION >NUL 2>&1 |
| 1041 | IF "%ERRORLEVEL%"=="0" GOTO EXITLR | 1041 | IF "%ERRORLEVEL%"=="0" GOTO EXITLR |
| 1042 | 1042 | ||
| 1043 | REM Do we have PowerShell available? | 1043 | REM Do we have PowerShell available? |
| 1044 | PowerShell /? >NUL 2>&1 | 1044 | PowerShell /? >NUL 2>&1 |
| 1045 | IF NOT "%ERRORLEVEL%"=="0" GOTO EXITLR | 1045 | IF NOT "%ERRORLEVEL%"=="0" GOTO EXITLR |
| 1046 | 1046 | ||
| 1047 | :GETTEMPNAME | 1047 | :GETTEMPNAME |
| 1048 | SET TMPFILE=%TEMP%\LuaRocks-Elevator-%RANDOM%.bat | 1048 | SET TMPFILE=%TEMP%\LuaRocks-Elevator-%RANDOM%.bat |
| 1049 | IF EXIST "%TMPFILE%" GOTO :GETTEMPNAME | 1049 | IF EXIST "%TMPFILE%" GOTO :GETTEMPNAME |
| 1050 | 1050 | ||
| 1051 | ECHO @ECHO OFF > "%TMPFILE%" | 1051 | ECHO @ECHO OFF > "%TMPFILE%" |
| 1052 | ECHO CHDIR /D %CD% >> "%TMPFILE%" | 1052 | ECHO CHDIR /D %CD% >> "%TMPFILE%" |
| 1053 | ECHO ECHO %0 %* >> "%TMPFILE%" | 1053 | ECHO ECHO %0 %* >> "%TMPFILE%" |
| 1054 | ECHO ECHO. >> "%TMPFILE%" | 1054 | ECHO ECHO. >> "%TMPFILE%" |
| 1055 | ECHO CALL %0 %* >> "%TMPFILE%" | 1055 | ECHO CALL %0 %* >> "%TMPFILE%" |
| 1056 | ECHO ECHO. >> "%TMPFILE%" | 1056 | ECHO ECHO. >> "%TMPFILE%" |
| 1057 | ECHO ECHO Press any key to close this window... >> "%TMPFILE%" | 1057 | ECHO ECHO Press any key to close this window... >> "%TMPFILE%" |
| 1058 | ECHO PAUSE ^> NUL >> "%TMPFILE%" | 1058 | ECHO PAUSE ^> NUL >> "%TMPFILE%" |
| 1059 | ECHO DEL "%TMPFILE%" >> "%TMPFILE%" | 1059 | ECHO DEL "%TMPFILE%" >> "%TMPFILE%" |
| 1060 | 1060 | ||
| 1061 | ECHO Now retrying as a privileged user... | 1061 | ECHO Now retrying as a privileged user... |
| 1062 | PowerShell -Command (New-Object -com 'Shell.Application').ShellExecute('%TMPFILE%', '', '', 'runas') | 1062 | PowerShell -Command (New-Object -com 'Shell.Application').ShellExecute('%TMPFILE%', '', '', 'runas') |
| 1063 | 1063 | ||
| 1064 | :EXITLR | 1064 | :EXITLR |
| 1065 | exit /b %EXITCODE% | 1065 | exit /b %EXITCODE% |
| 1066 | ]]) | 1066 | ]]) |
| 1067 | f:close() | 1067 | f:close() |
| 1068 | print(S"Created LuaRocks command: $BINDIR\\"..c..".bat") | 1068 | print(S"Created LuaRocks command: $BINDIR\\"..c..".bat") |
| 1069 | end | 1069 | end |
| 1070 | 1070 | ||
| 1071 | -- *********************************************************** | 1071 | -- *********************************************************** |
| 1072 | -- Configure LuaRocks | 1072 | -- Configure LuaRocks |
| 1073 | -- *********************************************************** | 1073 | -- *********************************************************** |
| 1074 | 1074 | ||
| 1075 | restore_config_files() | 1075 | restore_config_files() |
| 1076 | print() | 1076 | print() |
| 1077 | print("Configuring LuaRocks...") | 1077 | print("Configuring LuaRocks...") |
| 1078 | 1078 | ||
| 1079 | -- Create hardcoded.lua | 1079 | -- Create hardcoded.lua |
| 1080 | 1080 | ||
| 1081 | local hardcoded_lua = S[[$LUADIR\luarocks\core\hardcoded.lua]] | 1081 | local hardcoded_lua = S[[$LUADIR\luarocks\core\hardcoded.lua]] |
| 1082 | 1082 | ||
| 1083 | os.remove(hardcoded_lua) | 1083 | os.remove(hardcoded_lua) |
| 1084 | 1084 | ||
| 1085 | vars.SYSTEM = USE_MINGW and "mingw" or "windows" | 1085 | vars.SYSTEM = USE_MINGW and "mingw" or "windows" |
| 1086 | 1086 | ||
| 1087 | local f = io.open(hardcoded_lua, "w") | 1087 | local f = io.open(hardcoded_lua, "w") |
| 1088 | f:write(S[=[ | 1088 | f:write(S[=[ |
| 1089 | return { | 1089 | return { |
| 1090 | LUA_INCDIR=[[$LUA_INCDIR]], | 1090 | LUA_INCDIR=[[$LUA_INCDIR]], |
| 1091 | LUA_LIBDIR=[[$LUA_LIBDIR]], | 1091 | LUA_LIBDIR=[[$LUA_LIBDIR]], |
| 1092 | LUA_BINDIR=[[$LUA_BINDIR]], | 1092 | LUA_BINDIR=[[$LUA_BINDIR]], |
| 1093 | LUA_INTERPRETER=[[$LUA_INTERPRETER]], | 1093 | LUA_INTERPRETER=[[$LUA_INTERPRETER]], |
| 1094 | SYSTEM = [[$SYSTEM]], | 1094 | SYSTEM = [[$SYSTEM]], |
| 1095 | PROCESSOR = [[$UNAME_M]], | 1095 | PROCESSOR = [[$UNAME_M]], |
| 1096 | PREFIX = [[$PREFIX]], | 1096 | PREFIX = [[$PREFIX]], |
| 1097 | SYSCONFDIR = [[$SYSCONFDIR]], | 1097 | SYSCONFDIR = [[$SYSCONFDIR]], |
| 1098 | WIN_TOOLS = [[$PREFIX/tools]], | 1098 | WIN_TOOLS = [[$PREFIX/tools]], |
| 1099 | ]=]) | 1099 | ]=]) |
| 1100 | if FORCE_CONFIG then | 1100 | if FORCE_CONFIG then |
| 1101 | f:write(" FORCE_CONFIG = true,\n") | 1101 | f:write(" FORCE_CONFIG = true,\n") |
| 1102 | end | 1102 | end |
| 1103 | f:write("}\n") | 1103 | f:write("}\n") |
| 1104 | f:close() | 1104 | f:close() |
| 1105 | print(S([[Created LuaRocks hardcoded settings file: $LUADIR\luarocks\core\hardcoded.lua]])) | 1105 | print(S([[Created LuaRocks hardcoded settings file: $LUADIR\luarocks\core\hardcoded.lua]])) |
| 1106 | 1106 | ||
| 1107 | -- create config file | 1107 | -- create config file |
| 1108 | if not exists(vars.SYSCONFDIR) then | 1108 | if not exists(vars.SYSCONFDIR) then |
| 1109 | mkdir(vars.SYSCONFDIR) | 1109 | mkdir(vars.SYSCONFDIR) |
| 1110 | end | 1110 | end |
| 1111 | if exists(vars.CONFIG_FILE) then | 1111 | if exists(vars.CONFIG_FILE) then |
| 1112 | local nname = backup(vars.CONFIG_FILE, vars.SYSCONFFILENAME..".bak") | 1112 | local nname = backup(vars.CONFIG_FILE, vars.SYSCONFFILENAME..".bak") |
| 1113 | print("***************") | 1113 | print("***************") |
| 1114 | print(S"*** WARNING *** LuaRocks config file already exists: '$CONFIG_FILE'. The old file has been renamed to '"..nname.."'") | 1114 | print(S"*** WARNING *** LuaRocks config file already exists: '$CONFIG_FILE'. The old file has been renamed to '"..nname.."'") |
| 1115 | print("***************") | 1115 | print("***************") |
| 1116 | end | 1116 | end |
| 1117 | local f = io.open(vars.CONFIG_FILE, "w") | 1117 | local f = io.open(vars.CONFIG_FILE, "w") |
| 1118 | f:write([=[ | 1118 | f:write([=[ |
| 1119 | rocks_trees = { | 1119 | rocks_trees = { |
| 1120 | ]=]) | 1120 | ]=]) |
| 1121 | if FORCE_CONFIG then | 1121 | if FORCE_CONFIG then |
| 1122 | f:write(" home..[[/luarocks]],\n") | 1122 | f:write(" home..[[/luarocks]],\n") |
| 1123 | end | 1123 | end |
| 1124 | f:write(S" { name = [[user]],\n") | 1124 | f:write(S" { name = [[user]],\n") |
| 1125 | f:write(S" root = home..[[/luarocks]],\n") | 1125 | f:write(S" root = home..[[/luarocks]],\n") |
| 1126 | f:write(S" },\n") | 1126 | f:write(S" },\n") |
| 1127 | f:write(S" { name = [[system]],\n") | 1127 | f:write(S" { name = [[system]],\n") |
| 1128 | f:write(S" root = [[$TREE_ROOT]],\n") | 1128 | f:write(S" root = [[$TREE_ROOT]],\n") |
| 1129 | if vars.TREE_BIN then | 1129 | if vars.TREE_BIN then |
| 1130 | f:write(S" bin_dir = [[$TREE_BIN]],\n") | 1130 | f:write(S" bin_dir = [[$TREE_BIN]],\n") |
| 1131 | end | 1131 | end |
| 1132 | if vars.TREE_CMODULE then | 1132 | if vars.TREE_CMODULE then |
| 1133 | f:write(S" lib_dir = [[$TREE_CMODULE]],\n") | 1133 | f:write(S" lib_dir = [[$TREE_CMODULE]],\n") |
| 1134 | end | 1134 | end |
| 1135 | if vars.TREE_LMODULE then | 1135 | if vars.TREE_LMODULE then |
| 1136 | f:write(S" lua_dir = [[$TREE_LMODULE]],\n") | 1136 | f:write(S" lua_dir = [[$TREE_LMODULE]],\n") |
| 1137 | end | 1137 | end |
| 1138 | f:write(S" },\n") | 1138 | f:write(S" },\n") |
| 1139 | f:write("}\n") | 1139 | f:write("}\n") |
| 1140 | f:write("variables = {\n") | 1140 | f:write("variables = {\n") |
| 1141 | if USE_MINGW and vars.LUA_RUNTIME == "MSVCRT" then | 1141 | if USE_MINGW and vars.LUA_RUNTIME == "MSVCRT" then |
| 1142 | f:write(" MSVCRT = 'm', -- make MinGW use MSVCRT.DLL as runtime\n") | 1142 | f:write(" MSVCRT = 'm', -- make MinGW use MSVCRT.DLL as runtime\n") |
| 1143 | else | 1143 | else |
| 1144 | f:write(" MSVCRT = '"..vars.LUA_RUNTIME.."',\n") | 1144 | f:write(" MSVCRT = '"..vars.LUA_RUNTIME.."',\n") |
| 1145 | end | 1145 | end |
| 1146 | f:write(S" LUALIB = '$LUA_LIBNAME',\n") | 1146 | f:write(S" LUALIB = '$LUA_LIBNAME',\n") |
| 1147 | if USE_MINGW then | 1147 | if USE_MINGW then |
| 1148 | f:write(S[[ | 1148 | f:write(S[[ |
| 1149 | CC = $MINGW_CC, | 1149 | CC = $MINGW_CC, |
| 1150 | MAKE = $MINGW_MAKE, | 1150 | MAKE = $MINGW_MAKE, |
| 1151 | RC = $MINGW_RC, | 1151 | RC = $MINGW_RC, |
| 1152 | LD = $MINGW_LD, | 1152 | LD = $MINGW_LD, |
| 1153 | AR = $MINGW_AR, | 1153 | AR = $MINGW_AR, |
| 1154 | RANLIB = $MINGW_RANLIB, | 1154 | RANLIB = $MINGW_RANLIB, |
| 1155 | ]]) | 1155 | ]]) |
| 1156 | end | 1156 | end |
| 1157 | f:write("}\n") | 1157 | f:write("}\n") |
| 1158 | f:write("verbose = false -- set to 'true' to enable verbose output\n") | 1158 | f:write("verbose = false -- set to 'true' to enable verbose output\n") |
| 1159 | f:close() | 1159 | f:close() |
| 1160 | 1160 | ||
| 1161 | print(S"Created LuaRocks config file: $CONFIG_FILE") | 1161 | print(S"Created LuaRocks config file: $CONFIG_FILE") |
| 1162 | 1162 | ||
| 1163 | 1163 | ||
| 1164 | print() | 1164 | print() |
| 1165 | print("Creating rocktrees...") | 1165 | print("Creating rocktrees...") |
| 1166 | if not exists(vars.TREE_ROOT) then | 1166 | if not exists(vars.TREE_ROOT) then |
| 1167 | mkdir(vars.TREE_ROOT) | 1167 | mkdir(vars.TREE_ROOT) |
| 1168 | print(S[[Created system rocktree : "$TREE_ROOT"]]) | 1168 | print(S[[Created system rocktree : "$TREE_ROOT"]]) |
| 1169 | else | 1169 | else |
| 1170 | print(S[[System rocktree exists : "$TREE_ROOT"]]) | 1170 | print(S[[System rocktree exists : "$TREE_ROOT"]]) |
| 1171 | end | 1171 | end |
| 1172 | 1172 | ||
| 1173 | vars.APPDATA = os.getenv("APPDATA") | 1173 | vars.APPDATA = os.getenv("APPDATA") |
| 1174 | vars.LOCAL_TREE = vars.APPDATA..[[\LuaRocks]] | 1174 | vars.LOCAL_TREE = vars.APPDATA..[[\LuaRocks]] |
| 1175 | if not exists(vars.LOCAL_TREE) then | 1175 | if not exists(vars.LOCAL_TREE) then |
| 1176 | mkdir(vars.LOCAL_TREE) | 1176 | mkdir(vars.LOCAL_TREE) |
| 1177 | print(S[[Created local user rocktree: "$LOCAL_TREE"]]) | 1177 | print(S[[Created local user rocktree: "$LOCAL_TREE"]]) |
| 1178 | else | 1178 | else |
| 1179 | print(S[[Local user rocktree exists : "$LOCAL_TREE"]]) | 1179 | print(S[[Local user rocktree exists : "$LOCAL_TREE"]]) |
| 1180 | end | 1180 | end |
| 1181 | 1181 | ||
| 1182 | -- Load registry information | 1182 | -- Load registry information |
| 1183 | if REGISTRY then | 1183 | if REGISTRY then |
| 1184 | -- expand template with correct path information | 1184 | -- expand template with correct path information |
| 1185 | print() | 1185 | print() |
| 1186 | print([[Loading registry information for ".rockspec" files]]) | 1186 | print([[Loading registry information for ".rockspec" files]]) |
| 1187 | exec( S[[win32\lua5.1\bin\lua5.1.exe "$PREFIX\LuaRocks.reg.lua" "$PREFIX\LuaRocks.reg.template"]] ) | 1187 | exec( S[[win32\lua5.1\bin\lua5.1.exe "$PREFIX\LuaRocks.reg.lua" "$PREFIX\LuaRocks.reg.template"]] ) |
| 1188 | exec( S[[regedit /S "$PREFIX\\LuaRocks.reg"]] ) | 1188 | exec( S[[regedit /S "$PREFIX\\LuaRocks.reg"]] ) |
| 1189 | end | 1189 | end |
| 1190 | 1190 | ||
| 1191 | -- *********************************************************** | 1191 | -- *********************************************************** |
| 1192 | -- Cleanup | 1192 | -- Cleanup |
| 1193 | -- *********************************************************** | 1193 | -- *********************************************************** |
| 1194 | -- remove registry related files, no longer needed | 1194 | -- remove registry related files, no longer needed |
| 1195 | exec( S[[del "$PREFIX\LuaRocks.reg.*" >NUL]] ) | 1195 | exec( S[[del "$PREFIX\LuaRocks.reg.*" >NUL]] ) |
| 1196 | 1196 | ||
| 1197 | -- *********************************************************** | 1197 | -- *********************************************************** |
| 1198 | -- Exit handlers | 1198 | -- Exit handlers |
| 1199 | -- *********************************************************** | 1199 | -- *********************************************************** |
| 1200 | vars.TREE_BIN = vars.TREE_BIN or vars.TREE_ROOT..[[\bin]] | 1200 | vars.TREE_BIN = vars.TREE_BIN or vars.TREE_ROOT..[[\bin]] |
| 1201 | vars.TREE_LMODULE = vars.TREE_LMODULE or vars.TREE_ROOT..[[\share\lua\]]..vars.LUA_VERSION | 1201 | vars.TREE_LMODULE = vars.TREE_LMODULE or vars.TREE_ROOT..[[\share\lua\]]..vars.LUA_VERSION |
| 1202 | vars.TREE_CMODULE = vars.TREE_CMODULE or vars.TREE_ROOT..[[\lib\lua\]]..vars.LUA_VERSION | 1202 | vars.TREE_CMODULE = vars.TREE_CMODULE or vars.TREE_ROOT..[[\lib\lua\]]..vars.LUA_VERSION |
| 1203 | print(S[[ | 1203 | print(S[[ |
| 1204 | 1204 | ||
| 1205 | ============================ | 1205 | ============================ |
| 1206 | == LuaRocks is installed! == | 1206 | == LuaRocks is installed! == |
| 1207 | ============================ | 1207 | ============================ |
| 1208 | 1208 | ||
| 1209 | 1209 | ||
| 1210 | You may want to add the following elements to your paths; | 1210 | You may want to add the following elements to your paths; |
| 1211 | Lua interpreter; | 1211 | Lua interpreter; |
| 1212 | PATH : $LUA_BINDIR | 1212 | PATH : $LUA_BINDIR |
| 1213 | PATHEXT : .LUA | 1213 | PATHEXT : .LUA |
| 1214 | LuaRocks; | 1214 | LuaRocks; |
| 1215 | PATH : $PREFIX | 1215 | PATH : $PREFIX |
| 1216 | LUA_PATH : $PREFIX\lua\?.lua;$PREFIX\lua\?\init.lua | 1216 | LUA_PATH : $PREFIX\lua\?.lua;$PREFIX\lua\?\init.lua |
| 1217 | Local user rocktree (Note: %APPDATA% is user dependent); | 1217 | Local user rocktree (Note: %APPDATA% is user dependent); |
| 1218 | PATH : %APPDATA%\LuaRocks\bin | 1218 | PATH : %APPDATA%\LuaRocks\bin |
| 1219 | LUA_PATH : %APPDATA%\LuaRocks\share\lua\$LUA_VERSION\?.lua;%APPDATA%\LuaRocks\share\lua\$LUA_VERSION\?\init.lua | 1219 | LUA_PATH : %APPDATA%\LuaRocks\share\lua\$LUA_VERSION\?.lua;%APPDATA%\LuaRocks\share\lua\$LUA_VERSION\?\init.lua |
| 1220 | LUA_CPATH: %APPDATA%\LuaRocks\lib\lua\$LUA_VERSION\?.dll | 1220 | LUA_CPATH: %APPDATA%\LuaRocks\lib\lua\$LUA_VERSION\?.dll |
| 1221 | System rocktree | 1221 | System rocktree |
| 1222 | PATH : $TREE_BIN | 1222 | PATH : $TREE_BIN |
| 1223 | LUA_PATH : $TREE_LMODULE\?.lua;$TREE_LMODULE\?\init.lua | 1223 | LUA_PATH : $TREE_LMODULE\?.lua;$TREE_LMODULE\?\init.lua |
| 1224 | LUA_CPATH: $TREE_CMODULE\?.dll | 1224 | LUA_CPATH: $TREE_CMODULE\?.dll |
| 1225 | 1225 | ||
| 1226 | Note that the %APPDATA% element in the paths above is user specific and it MUST be replaced by its actual value. | 1226 | Note that the %APPDATA% element in the paths above is user specific and it MUST be replaced by its actual value. |
| 1227 | For the current user that value is: $APPDATA. | 1227 | For the current user that value is: $APPDATA. |
| 1228 | 1228 | ||
| 1229 | ]]) | 1229 | ]]) |
| 1230 | os.exit(0) | 1230 | os.exit(0) |
