13 Commits

Author SHA1 Message Date
David Macek
541efef81b Add option to specify command to run in the .ini file 2015-11-17 22:15:24 +01:00
David Macek
f91905f6bb WIP: new icons 2015-11-15 17:48:27 +01:00
David Macek
58b5c72ead Add .ini files to backup field of PKGBUILD; Enable expansion of .ini files contents; Add a clean PATH template 2015-11-09 23:46:10 +01:00
David Macek
1a1c5866e0 Fixed indentation 2015-11-04 12:15:25 +01:00
David Macek
a05668dffc Fixed bad value of "Start in" field after pinning; plus various fixed:
- version information consolidated into version.h
- removed strip from Makefile
- updated PKGBUILD
- fixed minor things in launcher.c
- added header guards
2015-11-04 12:11:00 +01:00
David Macek
551bb174b0 Fix MSYSTEM variable detection 2015-10-29 18:09:58 +01:00
David Macek
afa868fd7b Add PKGBUILD 2015-10-28 23:35:42 +01:00
David Macek
619f3830af Set CHERE_INVOKING and MSYSCON 2015-10-28 23:17:14 +01:00
David Macek
174fc35707 Bump version to 0.2 2015-10-28 23:00:55 +01:00
David Macek
292186be44 Refactored path handling; environment is now read from a file 2015-10-28 23:00:42 +01:00
David Macek
2c0e3b8e0c Allow passing arguments in order to launch a command 2015-10-28 22:00:55 +01:00
David Macek
ee4a2d0fe9 Switch to C11; refactor error reporting; switch to dynamic buffer allocation 2015-10-28 21:19:26 +01:00
David Macek
6a011ed295 Switch to unicode; make launcher compatible with new mintty 2015-10-28 20:49:37 +01:00
13 changed files with 103 additions and 175 deletions

View File

@@ -1,4 +0,0 @@
root = true
[*.{c,h}]
indent_style = tab

19
.gitignore vendored
View File

@@ -1,6 +1,13 @@
/msys.exe
/msys.res
/msys.ini
/mingw.exe
/mingw.res
/mingw.ini
/mingw32.exe
/mingw32.res
/mingw32.ini
/mingw64.exe
/mingw64.res
/mingw64.ini
/msys2.exe
/msys2.res
/msys2.ini
/pkg/
/src/
/*.pkg.tar.xz
/*.pkg.tar.xz.sig

View File

@@ -1,22 +1,29 @@
PREFIX=
msys: msys.exe msys.ini mingw.exe mingw.ini
all: msys
all: msys2.exe msys2.ini mingw32.exe mingw32.ini mingw64.exe mingw64.ini
.PHONY: all msys
.PHONY: all
msys.ini: launcher.ini
msys2.ini: launcher.ini
cp -f $^ $@
echo MSYSTEM=MSYS>> $@
msys.res: launcher.rc msys.ico
$(PREFIX)windres -O COFF -o $@ $< -DMSYSTEM=MSYS -DICONFILE=msys.ico
msys.exe: launcher.c msys.res
$(PREFIX)gcc -std=c11 -Wall -Wextra -Werror -municode -mwindows -o $@ $^ -luuid -lshlwapi -lpsapi
msys2.res: launcher.rc msys2.ico
$(PREFIX)windres -O COFF -o $@ $< -DMSYSTEM=MSYS -DICONFILE=msys2.ico
msys2.exe: launcher.c msys2.res
$(PREFIX)gcc -std=c11 -Wall -Wextra -Werror -static -municode -mwindows -o $@ $^
mingw.ini: launcher.ini
mingw32.ini: launcher.ini
cp -f $^ $@
echo MSYSTEM=MINGW32>> $@
mingw.res: launcher.rc mingw.ico
$(PREFIX)windres -O COFF -o $@ $< -DMSYSTEM=MINGW32 -DICONFILE=mingw.ico
mingw.exe: launcher.c mingw.res
$(PREFIX)gcc -std=c11 -Wall -Wextra -Werror -municode -mwindows -o $@ $^ -luuid -lshlwapi -lpsapi
mingw32.res: launcher.rc mingw32.ico
$(PREFIX)windres -O COFF -o $@ $< -DMSYSTEM=MINGW32 -DICONFILE=mingw32.ico
mingw32.exe: launcher.c mingw32.res
$(PREFIX)gcc -std=c11 -Wall -Wextra -Werror -static -municode -mwindows -o $@ $^
mingw64.ini: launcher.ini
cp -f $^ $@
echo MSYSTEM=MINGW64>> $@
mingw64.res: launcher.rc mingw64.ico
$(PREFIX)windres -O COFF -o $@ $< -DMSYSTEM=MINGW64 -DICONFILE=mingw64.ico
mingw64.exe: launcher.c mingw64.res
$(PREFIX)gcc -std=c11 -Wall -Wextra -Werror -static -municode -mwindows -o $@ $^

36
PKGBUILD Normal file
View File

@@ -0,0 +1,36 @@
_realname="msys2-launcher"
pkgname=("${_realname}-git")
pkgver=0.3.17.1a1c586
pkgrel=1
pkgdesc="Helper for launching MSYS2 shells"
arch=('x86_64' 'i686')
license=('MIT')
backup=({mingw32,mingw64,msys2}.ini)
provides=("${_realname}")
conflicts=("${_realname}")
depends=("mintty>=2.2.1")
makedepends=('mingw-w64-cross-gcc')
source=(launcher.{c,ini,rc} {macros,version}.h Makefile {mingw32,mingw64,msys2}.ico)
md5sums=('e21db11d21f95aab30966a8c528efd9b'
'7ab96cb34fef046e4839e270f9397a32'
'3a3c9fd8d083716e5efd759641eb4f31'
'57a40ae9972dac94df0830a1ab480895'
'fef245f65b6826502b953b81fb397d97'
'8d3fa1f8eb06343a13b72299c164f6cd'
'797a8ea3012b22705caadcb17b1291c2'
'0237b204a9d09dcadc955b435cefd311'
'292ad5cdd78abac9d694cc06819a96fc')
pkgver() {
local _major=$(cat version.h | grep -F 'VER_MAJOR' | head -1 | sed -e 's/.* //')
local _minor=$(cat version.h | grep -F 'VER_MINOR' | head -1 | sed -e 's/.* //')
printf "%s.%s.%s.%s" "${_major}" "${_minor}" "$(git rev-list --count HEAD)" "$(git rev-parse --short HEAD)"
}
build() {
make PREFIX=/opt/bin/${CARCH}-w64-mingw32-
}
package() {
cp {mingw32,mingw64,msys2}.{exe,ini} "${pkgdir}"
}

View File

@@ -1,9 +1,9 @@
Msys launcher
MSYS2 launcher
==============
A helper for launching Msys shells, adapted from the MSYS2 launcher. Features almost blink-less launching and correct taskbar/start pinning.
A helper for launching MSYS2 shells. Features blink-less launching and correct taskbar/start pinning.
Installation
------------
Just `make` and put the executables inside your Msys root.
Just `make` and put the executables inside your MSYS2 root. Needs mintty v2.1.6 or newer (unreleased at the time of writing).

View File

@@ -3,14 +3,6 @@
#define WIN32_LEAN_AND_MEAN
#define PSAPI_VERSION 1
#include <windows.h>
#include <objbase.h>
#include <propvarutil.h>
#include <shobjidl.h>
#include <shellapi.h>
#include <propsys.h>
#include <propkey.h>
#include <processthreadsapi.h>
#include <psapi.h>
#include <stdlib.h>
#include <stdbool.h>
#include <stdio.h>
@@ -21,11 +13,6 @@
// if any of the properties change, it's best to use a brand new AppID
#define APPID_REVISION 9
struct MainWindow {
DWORD pid;
HWND handle;
};
static void ShowError(const wchar_t* desc, const wchar_t* err, const long code) {
wchar_t msg[1024];
@@ -69,7 +56,7 @@ static PROCESS_INFORMATION StartChild(wchar_t* cmdline) {
return pi;
}
static wchar_t* SetEnv(wchar_t* conffile) {
static wchar_t* SetEnv(wchar_t* conffile, wchar_t** command) {
int code;
size_t buflen;
size_t expandedlen;
@@ -78,7 +65,9 @@ static wchar_t* SetEnv(wchar_t* conffile) {
wchar_t* expanded;
wchar_t* msystem;
FILE* handle;
bool specialvar;
*command = NULL;
msystem = NULL;
handle = _wfopen(conffile, L"rt");
@@ -110,6 +99,10 @@ static wchar_t* SetEnv(wchar_t* conffile) {
}
if (*buf != L'\0' && *buf != L'#') {
specialvar = *buf == L'=';
if (specialvar) {
++buf;
}
tmp = wcschr(buf, L'=');
if (tmp != NULL) {
*tmp++ = L'\0';
@@ -131,9 +124,15 @@ static wchar_t* SetEnv(wchar_t* conffile) {
return NULL;
}
}
code = SetEnvironmentVariable(buf, expanded);
if (code == 0) {
ShowLastError(L"Could not set environment variable");
if (specialvar) {
if (0 == wcsicmp(L"command", buf)) {
*command = _wcsdup(expanded);
}
} else {
code = SetEnvironmentVariable(buf, expanded);
if (code == 0) {
ShowLastError(L"Could not set environment variable");
}
}
} else {
ShowError(L"Could not parse environment line", buf, 0);
@@ -154,54 +153,9 @@ static wchar_t* SetEnv(wchar_t* conffile) {
return msystem;
}
static bool IsMainWindow(HWND handle) {
return GetWindow(handle, GW_OWNER) == (HWND)0 && IsWindowVisible(handle);
}
static BOOL CALLBACK CheckWindow(HWND handle, LPARAM lParam) {
struct MainWindow* data = (struct MainWindow*)lParam;
DWORD pid = 0;
GetWindowThreadProcessId(handle, &pid);
if (data->pid != pid || !IsMainWindow(handle)) {
return TRUE;
}
data->handle = handle;
return FALSE;
}
static HWND FindMainWindow(DWORD pid) {
struct MainWindow data;
data.pid = pid;
data.handle = 0;
EnumWindows(CheckWindow, (LPARAM)&data);
return data.handle;
}
HRESULT SetAppUserModelProperty(IPropertyStore* store, const PROPERTYKEY* key, LPCWSTR value) {
PROPVARIANT propVariant;
HRESULT hr;
propVariant.vt = VT_LPWSTR;
hr = SHStrDupW(value, &propVariant.pwszVal);
if (FAILED(hr)) {
return hr;
}
hr = store->lpVtbl->SetValue(store, key, &propVariant);
if (FAILED(hr)) {
return hr;
}
return 0;
}
int wmain(int argc, wchar_t* argv[]) {
PROCESS_INFORMATION child;
int code;
int delay = 10;
HWND window;
IPropertyStore* store;
HRESULT hr;
size_t buflen;
wchar_t* buf;
wchar_t* tmp;
@@ -210,24 +164,6 @@ int wmain(int argc, wchar_t* argv[]) {
wchar_t msysdir[PATH_MAX];
wchar_t exepath[PATH_MAX];
wchar_t confpath[PATH_MAX];
wchar_t wdpath[PATH_MAX];
const size_t proplen = 100;
wchar_t prop[proplen];
code = GetCurrentDirectory(PATH_MAX, wdpath);
if (code == 0 || code > PATH_MAX) {
ShowErrno(L"Could not determine working directory");
return __LINE__;
}
tmp = wdpath;
while (true) {
tmp = wcschr(tmp, L'\\');
if (tmp == NULL) {
break;
}
*tmp = L'/';
}
code = GetModuleFileName(NULL, exepath, sizeof(exepath) / sizeof(exepath[0]));
if (code == 0) {
@@ -270,7 +206,7 @@ int wmain(int argc, wchar_t* argv[]) {
}
}
msystem = SetEnv(confpath);
msystem = SetEnv(confpath, &args);
if (msystem == NULL) {
ShowError(L"Did not find the MSYSTEM variable", confpath, 0);
return __LINE__;
@@ -281,14 +217,16 @@ int wmain(int argc, wchar_t* argv[]) {
ShowLastError(L"Could not set environment variable");
}
// can break, but hopefully won't for most use cases
args = GetCommandLine();
if (args[0] == L'"') {
args++;
}
args += wcslen(argv[0]);
if (args[0] == L'"') {
args++;
if (argc > 1) {
// can break, but hopefully won't for most use cases
args = GetCommandLine();
if (*args == L'"') {
args++;
}
args += wcslen(argv[0]);
if (*args == L'"') {
args++;
}
}
code = -1;
@@ -300,7 +238,7 @@ int wmain(int argc, wchar_t* argv[]) {
ShowError(L"Could not allocate memory", L"", 0);
return __LINE__;
}
code = swprintf(buf, buflen, L"%s\\bin\\mintty.exe -i '%s' -- /bin/bash --login -c 'cd \\'%s\\'; exec %s'", msysdir, exepath, wdpath, argc == 1 ? L"/bin/bash -i" : args);
code = swprintf(buf, buflen, L"%s\\usr\\bin\\mintty.exe -i '%s' -o 'AppLaunchCmd=%s' -o 'AppID=MSYS2.Shell.%s.%d' -o 'AppName=MSYS2 %s Shell' --store-taskbar-properties -- /usr/bin/bash --login %s %s", msysdir, exepath, exepath, msystem, APPID_REVISION, msystem, args != NULL ? L"-c '$0 \"$@\"'" : L"-i" , args != NULL ? args : L"");
buflen *= 2;
}
if (code < 0) {
@@ -316,61 +254,5 @@ int wmain(int argc, wchar_t* argv[]) {
free(buf);
buf = NULL;
while (true) {
Sleep(delay);
window = FindMainWindow(GetProcessId(child.hProcess));
if (!window) {
delay *= 2;
if (delay > 60000) {
return __LINE__;
}
continue;
}
hr = SHGetPropertyStoreForWindow(window, &IID_IPropertyStore, (void**)&store);
if (FAILED(hr)) {
return __LINE__;
}
code = swprintf(prop, proplen, L"Msys.Shell.%s.%d", msystem, APPID_REVISION);
if (code < 0) {
ShowErrno(L"Could not write to buffer");
return __LINE__;
}
hr = SetAppUserModelProperty(store, &PKEY_AppUserModel_ID, prop);
if (FAILED(hr)) {
return __LINE__;
}
code = swprintf(prop, proplen, L"Msys %s Shell", msystem);
if (code < 0) {
ShowErrno(L"Could not write to buffer");
return __LINE__;
}
hr = SetAppUserModelProperty(store, &PKEY_AppUserModel_RelaunchDisplayNameResource, prop);
if (FAILED(hr)) {
return __LINE__;
}
hr = SetAppUserModelProperty(store, &PKEY_AppUserModel_RelaunchCommand, exepath);
if (FAILED(hr)) {
return __LINE__;
}
hr = SetAppUserModelProperty(store, &PKEY_AppUserModel_RelaunchIconResource, exepath);
if (FAILED(hr)) {
return __LINE__;
}
hr = store->lpVtbl->Commit(store);
if (FAILED(hr)) {
return __LINE__;
}
store->lpVtbl->Release(store);
store = NULL;
break;
}
return 0;
}

View File

@@ -8,8 +8,8 @@ BEGIN
BEGIN
BLOCK "040904E4"
BEGIN
VALUE "ProductName", "Msys"
VALUE "FileDescription", "Msys " STRINGIFY_A(MSYSTEM) " shell launcher"
VALUE "ProductName", "MSYS2"
VALUE "FileDescription", "MSYS2 " STRINGIFY_A(MSYSTEM) " shell launcher"
VALUE "FileVersion", STRINGIFY_A(VER_MAJOR) "." STRINGIFY_A(VER_MINOR)
END
END

BIN
mingw.ico

Binary file not shown.

Before

Width:  |  Height:  |  Size: 2.2 KiB

BIN
mingw32.ico Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 25 KiB

BIN
mingw64.ico Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 25 KiB

BIN
msys.ico

Binary file not shown.

Before

Width:  |  Height:  |  Size: 37 KiB

BIN
msys2.ico Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 25 KiB

View File

@@ -2,6 +2,6 @@
#define M2L_VERSION_H
#define VER_MAJOR 0
#define VER_MINOR 1
#define VER_MINOR 3
#endif