From 57df34fd1eec95285f2d058fc7cdbe9602f8aced Mon Sep 17 00:00:00 2001 From: Kevin Yue Date: Mon, 9 May 2022 21:58:58 +0800 Subject: [PATCH] Prepare release 1.4.3 (#149) * add inih * add configuration file for gpservice * Disable the UI configuration for extra args * remove VERSION_SUFFIX * remove ppa-publish.sh * Use Git repo as the source for PKGBUILD * remove VERSION_SUFFIX * Use Git repo as the source for PKGBUILD * add .install for PKGBUILD * add configuration file * Fix cmake * Fix cmake * Disable snap job * update AUR packaging * Disable the UI configuration for extra args * improve packaging script * update README.md * restart gpservice after package upgrading --- .editorconfig | 3 - .github/workflows/build.yml | 11 +- 3rdparty/inih/CMakeLists.txt | 11 + 3rdparty/inih/LICENSE.txt | 27 ++ 3rdparty/inih/cpp/INIReader.cpp | 116 +++++++ 3rdparty/inih/cpp/INIReader.h | 94 ++++++ 3rdparty/inih/ini.c | 298 ++++++++++++++++++ 3rdparty/inih/ini.h | 178 +++++++++++ CMakeLists.txt | 7 +- GPClient/gpclient.cpp | 4 +- GPClient/settingsdialog.ui | 5 +- GPClient/vpn.h | 2 +- GPClient/vpn_dbus.cpp | 4 +- GPClient/vpn_dbus.h | 2 +- GPClient/vpn_json.cpp | 2 +- GPClient/vpn_json.h | 2 +- GPService/CMakeLists.txt | 3 + GPService/gp.conf | 17 + GPService/gpservice.cpp | 22 +- GPService/gpservice.h | 5 +- README.md | 26 +- VERSION | 2 +- VERSION_SUFFIX | 0 cmake/FindNetworkManager.cmake | 59 ++++ packaging/aur/PKGBUILD | 33 -- .../aur/{PKGBUILD-git => PKGBUILD-git.in} | 25 +- packaging/aur/gp.install | 8 + packaging/obs/globalprotect-openconnect.spec | 6 +- scripts/_archive-all.sh | 6 +- scripts/ppa-publish.sh | 53 ---- scripts/prepare-packaging.sh | 16 +- scripts/release.sh | 3 - scripts/snapshot-archive-all.sh | 3 - scripts/snapshot-version.sh | 3 +- snap/snapcraft.yaml | 2 +- version.h.in | 2 +- 36 files changed, 901 insertions(+), 159 deletions(-) create mode 100644 3rdparty/inih/CMakeLists.txt create mode 100644 3rdparty/inih/LICENSE.txt create mode 100644 3rdparty/inih/cpp/INIReader.cpp create mode 100644 3rdparty/inih/cpp/INIReader.h create mode 100644 3rdparty/inih/ini.c create mode 100644 3rdparty/inih/ini.h create mode 100644 GPService/gp.conf delete mode 100644 VERSION_SUFFIX create mode 100644 cmake/FindNetworkManager.cmake delete mode 100644 packaging/aur/PKGBUILD rename packaging/aur/{PKGBUILD-git => PKGBUILD-git.in} (60%) create mode 100755 packaging/aur/gp.install delete mode 100755 scripts/ppa-publish.sh diff --git a/.editorconfig b/.editorconfig index 34a5079..ad0694f 100644 --- a/.editorconfig +++ b/.editorconfig @@ -9,8 +9,5 @@ trim_trailing_whitespace=true indent_style = space indent_size = 4 -[{VERSION,VERSION_SUFFIX}] -insert_final_newline = false - [*.sh] indent_style = tab diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml index 619d861..5960059 100644 --- a/.github/workflows/build.yml +++ b/.github/workflows/build.yml @@ -93,13 +93,11 @@ jobs: path: artifacts - name: Publish AUR package - env: - VERSION: $(cat ./artifacts/VERSION) uses: yuezk/github-actions-deploy-aur@update-pkgver with: pkgname: globalprotect-openconnect-git pkgbuild: ./artifacts/aur/PKGBUILD - assets: ./artifacts/aur/*.tar.gz + assets: ./artifacts/aur/gp.install update_pkgver: true commit_username: ${{ secrets.AUR_USERNAME }} commit_email: ${{ secrets.AUR_EMAIL }} @@ -126,7 +124,8 @@ jobs: files: ./artifacts/obs/* snapshot-snap: - if: ${{ github.event_name != 'pull_request' && github.ref == 'refs/heads/develop' }} + # if: ${{ github.event_name != 'pull_request' && github.ref == 'refs/heads/develop' }} + if: ${{ false }} needs: snapshot-archive-all runs-on: ubuntu-latest @@ -216,13 +215,11 @@ jobs: path: artifacts - name: Publish AUR package - env: - VERSION: $(cat ./artifacts/VERSION) uses: yuezk/github-actions-deploy-aur@update-pkgver with: pkgname: globalprotect-openconnect-git pkgbuild: ./artifacts/aur/PKGBUILD - assets: ./artifacts/aur/*.tar.gz + assets: ./artifacts/aur/gp.install update_pkgver: true commit_username: ${{ secrets.AUR_USERNAME }} commit_email: ${{ secrets.AUR_EMAIL }} diff --git a/3rdparty/inih/CMakeLists.txt b/3rdparty/inih/CMakeLists.txt new file mode 100644 index 0000000..f580de8 --- /dev/null +++ b/3rdparty/inih/CMakeLists.txt @@ -0,0 +1,11 @@ +cmake_minimum_required(VERSION 3.10.0) + +project(inih) + +add_library(inih STATIC + ini.h + ini.c + cpp/INIReader.h + cpp/INIReader.cpp +) +target_include_directories(inih PUBLIC "${CMAKE_CURRENT_SOURCE_DIR}/cpp") \ No newline at end of file diff --git a/3rdparty/inih/LICENSE.txt b/3rdparty/inih/LICENSE.txt new file mode 100644 index 0000000..cb7ee2d --- /dev/null +++ b/3rdparty/inih/LICENSE.txt @@ -0,0 +1,27 @@ + +The "inih" library is distributed under the New BSD license: + +Copyright (c) 2009, Ben Hoyt +All rights reserved. + +Redistribution and use in source and binary forms, with or without +modification, are permitted provided that the following conditions are met: + * Redistributions of source code must retain the above copyright + notice, this list of conditions and the following disclaimer. + * Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in the + documentation and/or other materials provided with the distribution. + * Neither the name of Ben Hoyt nor the names of its contributors + may be used to endorse or promote products derived from this software + without specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY BEN HOYT ''AS IS'' AND ANY +EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +DISCLAIMED. IN NO EVENT SHALL BEN HOYT BE LIABLE FOR ANY +DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND +ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. diff --git a/3rdparty/inih/cpp/INIReader.cpp b/3rdparty/inih/cpp/INIReader.cpp new file mode 100644 index 0000000..1bdac40 --- /dev/null +++ b/3rdparty/inih/cpp/INIReader.cpp @@ -0,0 +1,116 @@ +// Read an INI file into easy-to-access name/value pairs. + +// SPDX-License-Identifier: BSD-3-Clause + +// Copyright (C) 2009-2020, Ben Hoyt + +// inih and INIReader are released under the New BSD license (see LICENSE.txt). +// Go to the project home page for more info: +// +// https://github.com/benhoyt/inih + +#include +#include +#include +#include "../ini.h" +#include "INIReader.h" + +using std::string; + +INIReader::INIReader(const string& filename) +{ + _error = ini_parse(filename.c_str(), ValueHandler, this); +} + +INIReader::INIReader(const char *buffer, size_t buffer_size) +{ + string content(buffer, buffer_size); + _error = ini_parse_string(content.c_str(), ValueHandler, this); +} + +int INIReader::ParseError() const +{ + return _error; +} + +string INIReader::Get(const string& section, const string& name, const string& default_value) const +{ + string key = MakeKey(section, name); + // Use _values.find() here instead of _values.at() to support pre C++11 compilers + return _values.count(key) ? _values.find(key)->second : default_value; +} + +string INIReader::GetString(const string& section, const string& name, const string& default_value) const +{ + const string str = Get(section, name, ""); + return str.empty() ? default_value : str; +} + +long INIReader::GetInteger(const string& section, const string& name, long default_value) const +{ + string valstr = Get(section, name, ""); + const char* value = valstr.c_str(); + char* end; + // This parses "1234" (decimal) and also "0x4D2" (hex) + long n = strtol(value, &end, 0); + return end > value ? n : default_value; +} + +double INIReader::GetReal(const string& section, const string& name, double default_value) const +{ + string valstr = Get(section, name, ""); + const char* value = valstr.c_str(); + char* end; + double n = strtod(value, &end); + return end > value ? n : default_value; +} + +bool INIReader::GetBoolean(const string& section, const string& name, bool default_value) const +{ + string valstr = Get(section, name, ""); + // Convert to lower case to make string comparisons case-insensitive + std::transform(valstr.begin(), valstr.end(), valstr.begin(), ::tolower); + if (valstr == "true" || valstr == "yes" || valstr == "on" || valstr == "1") + return true; + else if (valstr == "false" || valstr == "no" || valstr == "off" || valstr == "0") + return false; + else + return default_value; +} + +bool INIReader::HasSection(const string& section) const +{ + const string key = MakeKey(section, ""); + std::map::const_iterator pos = _values.lower_bound(key); + if (pos == _values.end()) + return false; + // Does the key at the lower_bound pos start with "section"? + return pos->first.compare(0, key.length(), key) == 0; +} + +bool INIReader::HasValue(const string& section, const string& name) const +{ + string key = MakeKey(section, name); + return _values.count(key); +} + +string INIReader::MakeKey(const string& section, const string& name) +{ + string key = section + "=" + name; + // Convert to lower case to make section/name lookups case-insensitive + std::transform(key.begin(), key.end(), key.begin(), ::tolower); + return key; +} + +int INIReader::ValueHandler(void* user, const char* section, const char* name, + const char* value) +{ + if (!name) // Happens when INI_CALL_HANDLER_ON_NEW_SECTION enabled + return 1; + INIReader* reader = static_cast(user); + string key = MakeKey(section, name); + if (reader->_values[key].size() > 0) + reader->_values[key] += "\n"; + reader->_values[key] += value ? value : ""; + return 1; +} diff --git a/3rdparty/inih/cpp/INIReader.h b/3rdparty/inih/cpp/INIReader.h new file mode 100644 index 0000000..1571756 --- /dev/null +++ b/3rdparty/inih/cpp/INIReader.h @@ -0,0 +1,94 @@ +// Read an INI file into easy-to-access name/value pairs. + +// SPDX-License-Identifier: BSD-3-Clause + +// Copyright (C) 2009-2020, Ben Hoyt + +// inih and INIReader are released under the New BSD license (see LICENSE.txt). +// Go to the project home page for more info: +// +// https://github.com/benhoyt/inih + +#ifndef INIREADER_H +#define INIREADER_H + +#include +#include + +// Visibility symbols, required for Windows DLLs +#ifndef INI_API +#if defined _WIN32 || defined __CYGWIN__ +# ifdef INI_SHARED_LIB +# ifdef INI_SHARED_LIB_BUILDING +# define INI_API __declspec(dllexport) +# else +# define INI_API __declspec(dllimport) +# endif +# else +# define INI_API +# endif +#else +# if defined(__GNUC__) && __GNUC__ >= 4 +# define INI_API __attribute__ ((visibility ("default"))) +# else +# define INI_API +# endif +#endif +#endif + +// Read an INI file into easy-to-access name/value pairs. (Note that I've gone +// for simplicity here rather than speed, but it should be pretty decent.) +class INIReader +{ +public: + // Construct INIReader and parse given filename. See ini.h for more info + // about the parsing. + INI_API explicit INIReader(const std::string& filename); + + // Construct INIReader and parse given buffer. See ini.h for more info + // about the parsing. + INI_API explicit INIReader(const char *buffer, size_t buffer_size); + + // Return the result of ini_parse(), i.e., 0 on success, line number of + // first error on parse error, or -1 on file open error. + INI_API int ParseError() const; + + // Get a string value from INI file, returning default_value if not found. + INI_API std::string Get(const std::string& section, const std::string& name, + const std::string& default_value) const; + + // Get a string value from INI file, returning default_value if not found, + // empty, or contains only whitespace. + INI_API std::string GetString(const std::string& section, const std::string& name, + const std::string& default_value) const; + + // Get an integer (long) value from INI file, returning default_value if + // not found or not a valid integer (decimal "1234", "-1234", or hex "0x4d2"). + INI_API long GetInteger(const std::string& section, const std::string& name, long default_value) const; + + // Get a real (floating point double) value from INI file, returning + // default_value if not found or not a valid floating point value + // according to strtod(). + INI_API double GetReal(const std::string& section, const std::string& name, double default_value) const; + + // Get a boolean value from INI file, returning default_value if not found or if + // not a valid true/false value. Valid true values are "true", "yes", "on", "1", + // and valid false values are "false", "no", "off", "0" (not case sensitive). + INI_API bool GetBoolean(const std::string& section, const std::string& name, bool default_value) const; + + // Return true if the given section exists (section must contain at least + // one name=value pair). + INI_API bool HasSection(const std::string& section) const; + + // Return true if a value exists with the given section and field names. + INI_API bool HasValue(const std::string& section, const std::string& name) const; + +private: + int _error; + std::map _values; + static std::string MakeKey(const std::string& section, const std::string& name); + static int ValueHandler(void* user, const char* section, const char* name, + const char* value); +}; + +#endif // INIREADER_H diff --git a/3rdparty/inih/ini.c b/3rdparty/inih/ini.c new file mode 100644 index 0000000..f8a3ea3 --- /dev/null +++ b/3rdparty/inih/ini.c @@ -0,0 +1,298 @@ +/* inih -- simple .INI file parser + +SPDX-License-Identifier: BSD-3-Clause + +Copyright (C) 2009-2020, Ben Hoyt + +inih is released under the New BSD license (see LICENSE.txt). Go to the project +home page for more info: + +https://github.com/benhoyt/inih + +*/ + +#if defined(_MSC_VER) && !defined(_CRT_SECURE_NO_WARNINGS) +#define _CRT_SECURE_NO_WARNINGS +#endif + +#include +#include +#include + +#include "ini.h" + +#if !INI_USE_STACK +#if INI_CUSTOM_ALLOCATOR +#include +void* ini_malloc(size_t size); +void ini_free(void* ptr); +void* ini_realloc(void* ptr, size_t size); +#else +#include +#define ini_malloc malloc +#define ini_free free +#define ini_realloc realloc +#endif +#endif + +#define MAX_SECTION 50 +#define MAX_NAME 50 + +/* Used by ini_parse_string() to keep track of string parsing state. */ +typedef struct { + const char* ptr; + size_t num_left; +} ini_parse_string_ctx; + +/* Strip whitespace chars off end of given string, in place. Return s. */ +static char* rstrip(char* s) +{ + char* p = s + strlen(s); + while (p > s && isspace((unsigned char)(*--p))) + *p = '\0'; + return s; +} + +/* Return pointer to first non-whitespace char in given string. */ +static char* lskip(const char* s) +{ + while (*s && isspace((unsigned char)(*s))) + s++; + return (char*)s; +} + +/* Return pointer to first char (of chars) or inline comment in given string, + or pointer to NUL at end of string if neither found. Inline comment must + be prefixed by a whitespace character to register as a comment. */ +static char* find_chars_or_comment(const char* s, const char* chars) +{ +#if INI_ALLOW_INLINE_COMMENTS + int was_space = 0; + while (*s && (!chars || !strchr(chars, *s)) && + !(was_space && strchr(INI_INLINE_COMMENT_PREFIXES, *s))) { + was_space = isspace((unsigned char)(*s)); + s++; + } +#else + while (*s && (!chars || !strchr(chars, *s))) { + s++; + } +#endif + return (char*)s; +} + +/* Similar to strncpy, but ensures dest (size bytes) is + NUL-terminated, and doesn't pad with NULs. */ +static char* strncpy0(char* dest, const char* src, size_t size) +{ + /* Could use strncpy internally, but it causes gcc warnings (see issue #91) */ + size_t i; + for (i = 0; i < size - 1 && src[i]; i++) + dest[i] = src[i]; + dest[i] = '\0'; + return dest; +} + +/* See documentation in header file. */ +int ini_parse_stream(ini_reader reader, void* stream, ini_handler handler, + void* user) +{ + /* Uses a fair bit of stack (use heap instead if you need to) */ +#if INI_USE_STACK + char line[INI_MAX_LINE]; + int max_line = INI_MAX_LINE; +#else + char* line; + size_t max_line = INI_INITIAL_ALLOC; +#endif +#if INI_ALLOW_REALLOC && !INI_USE_STACK + char* new_line; + size_t offset; +#endif + char section[MAX_SECTION] = ""; + char prev_name[MAX_NAME] = ""; + + char* start; + char* end; + char* name; + char* value; + int lineno = 0; + int error = 0; + +#if !INI_USE_STACK + line = (char*)ini_malloc(INI_INITIAL_ALLOC); + if (!line) { + return -2; + } +#endif + +#if INI_HANDLER_LINENO +#define HANDLER(u, s, n, v) handler(u, s, n, v, lineno) +#else +#define HANDLER(u, s, n, v) handler(u, s, n, v) +#endif + + /* Scan through stream line by line */ + while (reader(line, (int)max_line, stream) != NULL) { +#if INI_ALLOW_REALLOC && !INI_USE_STACK + offset = strlen(line); + while (offset == max_line - 1 && line[offset - 1] != '\n') { + max_line *= 2; + if (max_line > INI_MAX_LINE) + max_line = INI_MAX_LINE; + new_line = ini_realloc(line, max_line); + if (!new_line) { + ini_free(line); + return -2; + } + line = new_line; + if (reader(line + offset, (int)(max_line - offset), stream) == NULL) + break; + if (max_line >= INI_MAX_LINE) + break; + offset += strlen(line + offset); + } +#endif + + lineno++; + + start = line; +#if INI_ALLOW_BOM + if (lineno == 1 && (unsigned char)start[0] == 0xEF && + (unsigned char)start[1] == 0xBB && + (unsigned char)start[2] == 0xBF) { + start += 3; + } +#endif + start = lskip(rstrip(start)); + + if (strchr(INI_START_COMMENT_PREFIXES, *start)) { + /* Start-of-line comment */ + } +#if INI_ALLOW_MULTILINE + else if (*prev_name && *start && start > line) { + /* Non-blank line with leading whitespace, treat as continuation + of previous name's value (as per Python configparser). */ + if (!HANDLER(user, section, prev_name, start) && !error) + error = lineno; + } +#endif + else if (*start == '[') { + /* A "[section]" line */ + end = find_chars_or_comment(start + 1, "]"); + if (*end == ']') { + *end = '\0'; + strncpy0(section, start + 1, sizeof(section)); + *prev_name = '\0'; +#if INI_CALL_HANDLER_ON_NEW_SECTION + if (!HANDLER(user, section, NULL, NULL) && !error) + error = lineno; +#endif + } + else if (!error) { + /* No ']' found on section line */ + error = lineno; + } + } + else if (*start) { + /* Not a comment, must be a name[=:]value pair */ + end = find_chars_or_comment(start, "=:"); + if (*end == '=' || *end == ':') { + *end = '\0'; + name = rstrip(start); + value = end + 1; +#if INI_ALLOW_INLINE_COMMENTS + end = find_chars_or_comment(value, NULL); + if (*end) + *end = '\0'; +#endif + value = lskip(value); + rstrip(value); + + /* Valid name[=:]value pair found, call handler */ + strncpy0(prev_name, name, sizeof(prev_name)); + if (!HANDLER(user, section, name, value) && !error) + error = lineno; + } + else if (!error) { + /* No '=' or ':' found on name[=:]value line */ +#if INI_ALLOW_NO_VALUE + *end = '\0'; + name = rstrip(start); + if (!HANDLER(user, section, name, NULL) && !error) + error = lineno; +#else + error = lineno; +#endif + } + } + +#if INI_STOP_ON_FIRST_ERROR + if (error) + break; +#endif + } + +#if !INI_USE_STACK + ini_free(line); +#endif + + return error; +} + +/* See documentation in header file. */ +int ini_parse_file(FILE* file, ini_handler handler, void* user) +{ + return ini_parse_stream((ini_reader)fgets, file, handler, user); +} + +/* See documentation in header file. */ +int ini_parse(const char* filename, ini_handler handler, void* user) +{ + FILE* file; + int error; + + file = fopen(filename, "r"); + if (!file) + return -1; + error = ini_parse_file(file, handler, user); + fclose(file); + return error; +} + +/* An ini_reader function to read the next line from a string buffer. This + is the fgets() equivalent used by ini_parse_string(). */ +static char* ini_reader_string(char* str, int num, void* stream) { + ini_parse_string_ctx* ctx = (ini_parse_string_ctx*)stream; + const char* ctx_ptr = ctx->ptr; + size_t ctx_num_left = ctx->num_left; + char* strp = str; + char c; + + if (ctx_num_left == 0 || num < 2) + return NULL; + + while (num > 1 && ctx_num_left != 0) { + c = *ctx_ptr++; + ctx_num_left--; + *strp++ = c; + if (c == '\n') + break; + num--; + } + + *strp = '\0'; + ctx->ptr = ctx_ptr; + ctx->num_left = ctx_num_left; + return str; +} + +/* See documentation in header file. */ +int ini_parse_string(const char* string, ini_handler handler, void* user) { + ini_parse_string_ctx ctx; + + ctx.ptr = string; + ctx.num_left = strlen(string); + return ini_parse_stream((ini_reader)ini_reader_string, &ctx, handler, + user); +} diff --git a/3rdparty/inih/ini.h b/3rdparty/inih/ini.h new file mode 100644 index 0000000..d1a2ba8 --- /dev/null +++ b/3rdparty/inih/ini.h @@ -0,0 +1,178 @@ +/* inih -- simple .INI file parser + +SPDX-License-Identifier: BSD-3-Clause + +Copyright (C) 2009-2020, Ben Hoyt + +inih is released under the New BSD license (see LICENSE.txt). Go to the project +home page for more info: + +https://github.com/benhoyt/inih + +*/ + +#ifndef INI_H +#define INI_H + +/* Make this header file easier to include in C++ code */ +#ifdef __cplusplus +extern "C" { +#endif + +#include + +/* Nonzero if ini_handler callback should accept lineno parameter. */ +#ifndef INI_HANDLER_LINENO +#define INI_HANDLER_LINENO 0 +#endif + +/* Visibility symbols, required for Windows DLLs */ +#ifndef INI_API +#if defined _WIN32 || defined __CYGWIN__ +# ifdef INI_SHARED_LIB +# ifdef INI_SHARED_LIB_BUILDING +# define INI_API __declspec(dllexport) +# else +# define INI_API __declspec(dllimport) +# endif +# else +# define INI_API +# endif +#else +# if defined(__GNUC__) && __GNUC__ >= 4 +# define INI_API __attribute__ ((visibility ("default"))) +# else +# define INI_API +# endif +#endif +#endif + +/* Typedef for prototype of handler function. */ +#if INI_HANDLER_LINENO +typedef int (*ini_handler)(void* user, const char* section, + const char* name, const char* value, + int lineno); +#else +typedef int (*ini_handler)(void* user, const char* section, + const char* name, const char* value); +#endif + +/* Typedef for prototype of fgets-style reader function. */ +typedef char* (*ini_reader)(char* str, int num, void* stream); + +/* Parse given INI-style file. May have [section]s, name=value pairs + (whitespace stripped), and comments starting with ';' (semicolon). Section + is "" if name=value pair parsed before any section heading. name:value + pairs are also supported as a concession to Python's configparser. + + For each name=value pair parsed, call handler function with given user + pointer as well as section, name, and value (data only valid for duration + of handler call). Handler should return nonzero on success, zero on error. + + Returns 0 on success, line number of first error on parse error (doesn't + stop on first error), -1 on file open error, or -2 on memory allocation + error (only when INI_USE_STACK is zero). +*/ +INI_API int ini_parse(const char* filename, ini_handler handler, void* user); + +/* Same as ini_parse(), but takes a FILE* instead of filename. This doesn't + close the file when it's finished -- the caller must do that. */ +INI_API int ini_parse_file(FILE* file, ini_handler handler, void* user); + +/* Same as ini_parse(), but takes an ini_reader function pointer instead of + filename. Used for implementing custom or string-based I/O (see also + ini_parse_string). */ +INI_API int ini_parse_stream(ini_reader reader, void* stream, ini_handler handler, + void* user); + +/* Same as ini_parse(), but takes a zero-terminated string with the INI data +instead of a file. Useful for parsing INI data from a network socket or +already in memory. */ +INI_API int ini_parse_string(const char* string, ini_handler handler, void* user); + +/* Nonzero to allow multi-line value parsing, in the style of Python's + configparser. If allowed, ini_parse() will call the handler with the same + name for each subsequent line parsed. */ +#ifndef INI_ALLOW_MULTILINE +#define INI_ALLOW_MULTILINE 1 +#endif + +/* Nonzero to allow a UTF-8 BOM sequence (0xEF 0xBB 0xBF) at the start of + the file. See https://github.com/benhoyt/inih/issues/21 */ +#ifndef INI_ALLOW_BOM +#define INI_ALLOW_BOM 1 +#endif + +/* Chars that begin a start-of-line comment. Per Python configparser, allow + both ; and # comments at the start of a line by default. */ +#ifndef INI_START_COMMENT_PREFIXES +#define INI_START_COMMENT_PREFIXES ";#" +#endif + +/* Nonzero to allow inline comments (with valid inline comment characters + specified by INI_INLINE_COMMENT_PREFIXES). Set to 0 to turn off and match + Python 3.2+ configparser behaviour. */ +#ifndef INI_ALLOW_INLINE_COMMENTS +#define INI_ALLOW_INLINE_COMMENTS 1 +#endif +#ifndef INI_INLINE_COMMENT_PREFIXES +#define INI_INLINE_COMMENT_PREFIXES ";" +#endif + +/* Nonzero to use stack for line buffer, zero to use heap (malloc/free). */ +#ifndef INI_USE_STACK +#define INI_USE_STACK 1 +#endif + +/* Maximum line length for any line in INI file (stack or heap). Note that + this must be 3 more than the longest line (due to '\r', '\n', and '\0'). */ +#ifndef INI_MAX_LINE +#define INI_MAX_LINE 200 +#endif + +/* Nonzero to allow heap line buffer to grow via realloc(), zero for a + fixed-size buffer of INI_MAX_LINE bytes. Only applies if INI_USE_STACK is + zero. */ +#ifndef INI_ALLOW_REALLOC +#define INI_ALLOW_REALLOC 0 +#endif + +/* Initial size in bytes for heap line buffer. Only applies if INI_USE_STACK + is zero. */ +#ifndef INI_INITIAL_ALLOC +#define INI_INITIAL_ALLOC 200 +#endif + +/* Stop parsing on first error (default is to keep parsing). */ +#ifndef INI_STOP_ON_FIRST_ERROR +#define INI_STOP_ON_FIRST_ERROR 0 +#endif + +/* Nonzero to call the handler at the start of each new section (with + name and value NULL). Default is to only call the handler on + each name=value pair. */ +#ifndef INI_CALL_HANDLER_ON_NEW_SECTION +#define INI_CALL_HANDLER_ON_NEW_SECTION 0 +#endif + +/* Nonzero to allow a name without a value (no '=' or ':' on the line) and + call the handler with value NULL in this case. Default is to treat + no-value lines as an error. */ +#ifndef INI_ALLOW_NO_VALUE +#define INI_ALLOW_NO_VALUE 0 +#endif + +/* Nonzero to use custom ini_malloc, ini_free, and ini_realloc memory + allocation functions (INI_USE_STACK must also be 0). These functions must + have the same signatures as malloc/free/realloc and behave in a similar + way. ini_realloc is only needed if INI_ALLOW_REALLOC is set. */ +#ifndef INI_CUSTOM_ALLOCATOR +#define INI_CUSTOM_ALLOCATOR 0 +#endif + + +#ifdef __cplusplus +} +#endif + +#endif /* INI_H */ diff --git a/CMakeLists.txt b/CMakeLists.txt index 39a6fd4..fe2f4d7 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -1,5 +1,6 @@ cmake_minimum_required(VERSION 3.10.0) +set(CMAKE_MODULE_PATH "${CMAKE_SOURCE_DIR}/cmake;${CMAKE_MODULE_PATH}") set(CMAKE_CXX_STANDARD 11) set(CMAKE_CXX_STANDARD_REQUIRED ON) @@ -7,9 +8,8 @@ set(CMAKE_AUTOMOC ON) set(CMAKE_AUTORCC ON) set(CMAKE_AUTOUIC ON) -file(STRINGS "VERSION" ver) -file(STRINGS "VERSION_SUFFIX" VERSION_SUFFIX) -project(GlobalProtect-openconnect VERSION ${ver} LANGUAGES CXX) +file(STRINGS "VERSION" version) +project(GlobalProtect-openconnect LANGUAGES CXX) # Set the CMAKE_INSTALL_PREFIX to /usr if not specified if (CMAKE_INSTALL_PREFIX_INITIALIZED_TO_DEFAULT) @@ -31,6 +31,7 @@ find_package(Qt5 REQUIRED COMPONENTS ) add_subdirectory(3rdparty/qt-unix-signals) +add_subdirectory(3rdparty/inih) add_subdirectory(GPService) add_subdirectory(GPClient) add_dependencies(gpclient gpservice) diff --git a/GPClient/gpclient.cpp b/GPClient/gpclient.cpp index 8e56643..57e6445 100644 --- a/GPClient/gpclient.cpp +++ b/GPClient/gpclient.cpp @@ -68,14 +68,12 @@ void GPClient::setupSettings() void GPClient::onSettingsButtonClicked() { - settingsDialog->setExtraArgs(settings::get("extraArgs", "").toString()); settingsDialog->setClientos(settings::get("clientos", "Linux").toString()); settingsDialog->show(); } void GPClient::onSettingsAccepted() { - settings::save("extraArgs", settingsDialog->extraArgs()); settings::save("clientos", settingsDialog->clientos()); } @@ -378,7 +376,7 @@ void GPClient::onGatewaySuccess(const QString &authCookie) for (GPGateway &gw : allGateways()) { gatewayAddresses.push_back(gw.address()); } - vpn->connect(currentGateway().address(), gatewayAddresses, portalConfig.username(), authCookie, settings::get("extraArgs", "").toString()); + vpn->connect(currentGateway().address(), gatewayAddresses, portalConfig.username(), authCookie); ui->statusLabel->setText("Connecting..."); updateConnectionStatus(VpnStatus::pending); } diff --git a/GPClient/settingsdialog.ui b/GPClient/settingsdialog.ui index 4d140dc..7a595f3 100644 --- a/GPClient/settingsdialog.ui +++ b/GPClient/settingsdialog.ui @@ -33,8 +33,11 @@ + + true + - e.g. --name=value --script="vpn-slice xxx" + The configuration has been moved to "/etc/gpservice/gp.conf" diff --git a/GPClient/vpn.h b/GPClient/vpn.h index eb26f33..b389edd 100644 --- a/GPClient/vpn.h +++ b/GPClient/vpn.h @@ -8,7 +8,7 @@ class IVpn public: virtual ~IVpn() = default; - virtual void connect(const QString &preferredServer, const QList &servers, const QString &username, const QString &passwd, const QString &extraArgs) = 0; + virtual void connect(const QString &preferredServer, const QList &servers, const QString &username, const QString &passwd) = 0; virtual void disconnect() = 0; virtual int status() = 0; diff --git a/GPClient/vpn_dbus.cpp b/GPClient/vpn_dbus.cpp index 2983cd1..937d15d 100644 --- a/GPClient/vpn_dbus.cpp +++ b/GPClient/vpn_dbus.cpp @@ -1,7 +1,7 @@ #include "vpn_dbus.h" -void VpnDbus::connect(const QString &preferredServer, const QList &servers, const QString &username, const QString &passwd, const QString &extraArgs) { - inner->connect(preferredServer, username, passwd, extraArgs); +void VpnDbus::connect(const QString &preferredServer, const QList &servers, const QString &username, const QString &passwd) { + inner->connect(preferredServer, username, passwd); } void VpnDbus::disconnect() { diff --git a/GPClient/vpn_dbus.h b/GPClient/vpn_dbus.h index 28b24eb..107e3d8 100644 --- a/GPClient/vpn_dbus.h +++ b/GPClient/vpn_dbus.h @@ -20,7 +20,7 @@ public: QObject::connect(inner, &com::yuezk::qt::GPService::logAvailable, this, &VpnDbus::logAvailable); } - void connect(const QString &preferredServer, const QList &servers, const QString &username, const QString &passwd, const QString &extraArgs); + void connect(const QString &preferredServer, const QList &servers, const QString &username, const QString &passwd); void disconnect(); int status(); diff --git a/GPClient/vpn_json.cpp b/GPClient/vpn_json.cpp index bfdcf7f..78a35e5 100644 --- a/GPClient/vpn_json.cpp +++ b/GPClient/vpn_json.cpp @@ -4,7 +4,7 @@ #include #include -void VpnJson::connect(const QString &preferredServer, const QList &servers, const QString &username, const QString &passwd, const QString &extraArgs) { +void VpnJson::connect(const QString &preferredServer, const QList &servers, const QString &username, const QString &passwd) { QJsonArray sl; for (const QString &srv : servers) { sl.push_back(QJsonValue(srv)); diff --git a/GPClient/vpn_json.h b/GPClient/vpn_json.h index f577bee..8fbbfe0 100644 --- a/GPClient/vpn_json.h +++ b/GPClient/vpn_json.h @@ -10,7 +10,7 @@ class VpnJson : public QObject, public IVpn public: VpnJson(QObject *parent) : QObject(parent) {} - void connect(const QString &preferredServer, const QList &servers, const QString &username, const QString &passwd, const QString &extraArgs); + void connect(const QString &preferredServer, const QList &servers, const QString &username, const QString &passwd); void disconnect(); int status(); diff --git a/GPService/CMakeLists.txt b/GPService/CMakeLists.txt index 2fbc440..98e6b9b 100644 --- a/GPService/CMakeLists.txt +++ b/GPService/CMakeLists.txt @@ -22,6 +22,7 @@ qt5_add_dbus_adaptor( ) add_executable(gpservice + gpservice.h gpservice.cpp main.cpp ${gpservice_GENERATED_SOURCES} @@ -58,6 +59,7 @@ target_link_libraries(gpservice Qt5::Network Qt5::DBus QtSignals + inih ) target_compile_definitions(gpservice PUBLIC QAPPLICATION_CLASS=QCoreApplication) @@ -65,6 +67,7 @@ target_compile_definitions(gpservice PUBLIC QAPPLICATION_CLASS=QCoreApplication) install(TARGETS gpservice DESTINATION bin) install(FILES "dbus/com.yuezk.qt.GPService.conf" DESTINATION share/dbus-1/system.d ) install(FILES "${CMAKE_CURRENT_BINARY_DIR}/dbus/com.yuezk.qt.GPService.service" DESTINATION share/dbus-1/system-services) +install(FILES "gp.conf" DESTINATION /etc/gpservice) if("$ENV{DEBIAN_PACKAGE}") # Install the systemd unit files to /lib/systemd/system for debian package diff --git a/GPService/gp.conf b/GPService/gp.conf new file mode 100644 index 0000000..7d7f824 --- /dev/null +++ b/GPService/gp.conf @@ -0,0 +1,17 @@ +# Configuration file for GlobalProtect-openconnect +# +# Description: +# +# Each section is a VPN gateway address, and [*] is a special section that defines the default configuration. +# See https://github.com/yuezk/GlobalProtect-openconnect/wiki/Configuration for more details. +# +# Example: +# +# [*] +# openconnect-args= +# +# [vpn1.company.com] +# openconnect-args=--script=/path/to/vpnc-script + +[*] +openconnect-args= diff --git a/GPService/gpservice.cpp b/GPService/gpservice.cpp index 5623649..6fa6db8 100644 --- a/GPService/gpservice.cpp +++ b/GPService/gpservice.cpp @@ -5,6 +5,7 @@ #include #include +#include "INIReader.h" #include "gpservice.h" #include "gpserviceadaptor.h" @@ -41,8 +42,22 @@ QString GPService::findBinary() return nullptr; } +QString GPService::extraOpenconnectArgs(const QString &gateway) +{ + INIReader reader("/etc/gpservice/gp.conf"); + + if (reader.ParseError() < 0) { + return ""; + } + + std::string defaultArgs = reader.Get("*", "openconnect-args", ""); + std::string extraArgs = reader.Get(gateway.toStdString(), "openconnect-args", defaultArgs); + + return QString::fromStdString(extraArgs); +} + /* Port from https://github.com/qt/qtbase/blob/11d1dcc6e263c5059f34b44d531c9ccdf7c0b1d6/src/corelib/io/qprocess.cpp#L2115 */ -QStringList GPService::splitCommand(QString command) +QStringList GPService::splitCommand(const QString &command) { QStringList args; QString tmp; @@ -92,7 +107,7 @@ void GPService::quit() } } -void GPService::connect(QString server, QString username, QString passwd, QString extraArgs) +void GPService::connect(QString server, QString username, QString passwd) { if (vpnStatus != GPService::VpnNotConnected) { log("VPN status is: " + QVariant::fromValue(vpnStatus).toString()); @@ -110,6 +125,9 @@ void GPService::connect(QString server, QString username, QString passwd, QStrin return; } + const QString extraArgs = extraOpenconnectArgs(server); + log(QString("Got extra OpenConnect args for server: %1, %2").arg(server, extraArgs.isEmpty() ? "" : extraArgs)); + QStringList args; args << QCoreApplication::arguments().mid(1) << "--protocol=gp" diff --git a/GPService/gpservice.h b/GPService/gpservice.h index a3b4856..b36ae07 100644 --- a/GPService/gpservice.h +++ b/GPService/gpservice.h @@ -37,7 +37,7 @@ signals: void logAvailable(QString log); public slots: - void connect(QString server, QString username, QString passwd, QString extraArgs); + void connect(QString server, QString username, QString passwd); void disconnect(); int status(); @@ -56,7 +56,8 @@ private: void log(QString msg); bool isValidVersion(QString &bin); static QString findBinary(); - static QStringList splitCommand(QString command); + static QString extraOpenconnectArgs(const QString &gateway); + static QStringList splitCommand(const QString &command); }; #endif // GLOBALPROTECTSERVICE_H diff --git a/README.md b/README.md index d232e64..2cb0286 100644 --- a/README.md +++ b/README.md @@ -87,7 +87,7 @@ sudo dnf install globalprotect-openconnect 1. Add the repository: `https://download.opensuse.org/repositories/home:/yuezk/CentOS_8/home:yuezk.repo` 1. Install `globalprotect-openconnect` - + ## Build & Install from source code Clone this repo with: @@ -100,14 +100,14 @@ cd GlobalProtect-openconnect ### Ubuntu/Mint > **⚠️ REQUIRED for Ubuntu 18.04 ⚠️** -> +> > Add this [dwmw2/openconnect](https://launchpad.net/~dwmw2/+archive/ubuntu/openconnect) PPA first to install the latest openconnect. -> +> > ```sh > sudo add-apt-repository ppa:dwmw2/openconnect > sudo apt update > ``` - + Build and install with: ```sh @@ -155,7 +155,7 @@ Install the Qt5 dependencies and OpenConnect: # if you need a Host Integrity Protection report csdWrapper = "${pkgs.openconnect}/libexec/openconnect/hipreport.sh"; }; - + environment.systemPackages = [ globalprotect-openconnect ]; ``` @@ -165,14 +165,8 @@ Once the software is installed, you can run `gpclient` to start the UI. ## Passing the Custom Parameters to `OpenConnect` CLI -Custom parameters can be appended to the `OpenConnect` CLI with the following settings. +See [Configuration](https://github.com/yuezk/GlobalProtect-openconnect/wiki/Configuration) -> Tokens with spaces can be surrounded by double quotes; three consecutive double quotes represent the quote character itself. - -

- -

- ## Display the system tray icon on Gnome 40 Install the [AppIndicator and KStatusNotifierItem Support](https://extensions.gnome.org/extension/615/appindicator-support/) extension and you will see the system try icon (Restart the system after the installation). @@ -181,7 +175,7 @@ Install the [AppIndicator and KStatusNotifierItem Support](https://extensions.gn

- + ## Future plan @@ -189,11 +183,11 @@ Install the [AppIndicator and KStatusNotifierItem Support](https://extensions.gn - [ ] Process bugs and feature requests - [ ] Support for bypassing the `gpclient` parameters - [ ] Support the CLI mode - - + + ## Troubleshooting -The application logs can be found at: `~/.cache/GlobalProtect-openconnect/gpclient.log` +Run `gpclient` in the Terminal and collect the logs. ## [License](./LICENSE) GPLv3 diff --git a/VERSION b/VERSION index c9929e3..9df886c 100644 --- a/VERSION +++ b/VERSION @@ -1 +1 @@ -1.4.2 \ No newline at end of file +1.4.2 diff --git a/VERSION_SUFFIX b/VERSION_SUFFIX deleted file mode 100644 index e69de29..0000000 diff --git a/cmake/FindNetworkManager.cmake b/cmake/FindNetworkManager.cmake new file mode 100644 index 0000000..14da5d8 --- /dev/null +++ b/cmake/FindNetworkManager.cmake @@ -0,0 +1,59 @@ +# - Try to find NetworkManager +# Once done this will define +# +# NETWORKMANAGER_FOUND - system has NetworkManager +# NETWORKMANAGER_INCLUDE_DIRS - the NetworkManager include directories +# NETWORKMANAGER_LIBRARIES - the libraries needed to use NetworkManager +# NETWORKMANAGER_CFLAGS - Compiler switches required for using NetworkManager +# NETWORKMANAGER_VERSION - version number of NetworkManager + +# Copyright (c) 2006, Alexander Neundorf, +# Copyright (c) 2007, Will Stephenson, +# Copyright (c) 2015-2018, Jan Grulich, + +# Redistribution and use in source and binary forms, with or without +# modification, are permitted provided that the following conditions +# are met: +# 1. Redistributions of source code must retain the above copyright +# notice, this list of conditions and the following disclaimer. +# 2. Redistributions in binary form must reproduce the above copyright +# notice, this list of conditions and the following disclaimer in the +# documentation and/or other materials provided with the distribution. +# 3. Neither the name of the University nor the names of its contributors +# may be used to endorse or promote products derived from this software +# without specific prior written permission. +# +# THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND +# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +# ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE +# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +# SUCH DAMAGE. + +IF (NETWORKMANAGER_INCLUDE_DIRS) + # in cache already + SET(NetworkManager_FIND_QUIETLY TRUE) +ENDIF (NETWORKMANAGER_INCLUDE_DIRS) + +IF (NOT WIN32) + find_package(PkgConfig) + PKG_SEARCH_MODULE(NETWORKMANAGER libnm) + IF (NETWORKMANAGER_FOUND) + IF (NetworkManager_FIND_VERSION AND ("${NETWORKMANAGER_VERSION}" VERSION_LESS "${NetworkManager_FIND_VERSION}")) + MESSAGE(FATAL_ERROR "NetworkManager ${NETWORKMANAGER_VERSION} is too old, need at least ${NetworkManager_FIND_VERSION}") + ELSE () + IF (NOT NetworkManager_FIND_QUIETLY) + MESSAGE(STATUS "Found NetworkManager: ${NETWORKMANAGER_LIBRARY_DIRS}") + ENDIF () + ENDIF () + ELSE () + MESSAGE(FATAL_ERROR "Could NOT find NetworkManager, check FindPkgConfig output above!") + ENDIF () +ENDIF (NOT WIN32) + +MARK_AS_ADVANCED(NETWORKMANAGER_INCLUDE_DIRS) diff --git a/packaging/aur/PKGBUILD b/packaging/aur/PKGBUILD deleted file mode 100644 index f0d0451..0000000 --- a/packaging/aur/PKGBUILD +++ /dev/null @@ -1,33 +0,0 @@ -# Maintainer: Keinv Yue - -pkgname=globalprotect-openconnect -pkgver=0 -pkgrel=1 -pkgdesc="A GlobalProtect VPN client (GUI) for Linux based on Openconnect and built with Qt5, supports SAML auth mode." -arch=(x86_64 aarch64) -url="https://github.com/yuezk/GlobalProtect-openconnect" -license=('GPL3') -depends=('openconnect>=8.0.0' qt5-base qt5-webengine qt5-websockets) -makedepends=(cmake) -provides=('gpclient' 'gpservice') - -source=("${pkgname}.tar.gz") -sha256sums=('SKIP') - -pkgver() { - cd $srcdir/$pkgname-*/ - cat VERSION VERSION_SUFFIX -} - -build() { - cd $srcdir/$pkgname-*/ - cmake -B build \ - -DCMAKE_BUILD_TYPE=Release \ - -DCMAKE_CXX_FLAGS_RELEASE=-s - make -j$(nproc) -C build -} - -package() { - cd $srcdir/$pkgname-*/ - make DESTDIR="$pkgdir/" install -C build -} diff --git a/packaging/aur/PKGBUILD-git b/packaging/aur/PKGBUILD-git.in similarity index 60% rename from packaging/aur/PKGBUILD-git rename to packaging/aur/PKGBUILD-git.in index 7c54257..f4d5358 100644 --- a/packaging/aur/PKGBUILD-git +++ b/packaging/aur/PKGBUILD-git.in @@ -1,28 +1,33 @@ # Maintainer: Keinv Yue +_pkgver="{VERSION}" +_commit="{COMMIT}" pkgname=globalprotect-openconnect-git -_pkgname=globalprotect-openconnect -pkgver=0 +pkgver=${_pkgver} pkgrel=1 pkgdesc="A GlobalProtect VPN client (GUI) for Linux based on Openconnect and built with Qt5, supports SAML auth mode. (development version)" arch=(x86_64 aarch64) url="https://github.com/yuezk/GlobalProtect-openconnect" license=('GPL3') +backup=( + etc/gpservice/gp.conf +) +install=gp.install depends=('openconnect>=8.0.0' qt5-base qt5-webengine qt5-websockets) -makedepends=(cmake) +makedepends=(git cmake) conflicts=('globalprotect-openconnect') -provides=('gpclient' 'gpservice') +provides=('globalprotect-openconnect' 'gpclient' 'gpservice') -source=("${_pkgname}.tar.gz") +source=(git+https://github.com/yuezk/GlobalProtect-openconnect#commit=${_commit}) sha256sums=('SKIP') -pkgver() { - cd $srcdir/$_pkgname-*/ - cat VERSION VERSION_SUFFIX +prepare() { + cd GlobalProtect-openconnect + echo "${_pkgver}" > VERSION } build() { - cd $srcdir/${_pkgname}-*/ + cd GlobalProtect-openconnect cmake -B build \ -DCMAKE_BUILD_TYPE=Release \ -DCMAKE_CXX_FLAGS_RELEASE=-s @@ -30,6 +35,6 @@ build() { } package() { - cd $srcdir/${_pkgname}-*/ + cd GlobalProtect-openconnect make DESTDIR="$pkgdir/" install -C build } diff --git a/packaging/aur/gp.install b/packaging/aur/gp.install new file mode 100755 index 0000000..e2cabbc --- /dev/null +++ b/packaging/aur/gp.install @@ -0,0 +1,8 @@ +post_install() { + systemctl enable gpservice.service + systemctl restart gpservice.service +} + +post_upgrade() { + post_install +} \ No newline at end of file diff --git a/packaging/obs/globalprotect-openconnect.spec b/packaging/obs/globalprotect-openconnect.spec index 63b7626..bd02ca7 100644 --- a/packaging/obs/globalprotect-openconnect.spec +++ b/packaging/obs/globalprotect-openconnect.spec @@ -54,7 +54,7 @@ A GlobalProtect VPN client (GUI) for Linux based on OpenConnect and built with Q %if 0%{?suse_version} %service_del_postun gpservice.service %else - %systemd_postun gpservice.service + %systemd_postun_with_restart gpservice.service %endif @@ -73,7 +73,7 @@ A GlobalProtect VPN client (GUI) for Linux based on OpenConnect and built with Q %install %if 0%{?fedora_version} && 0%{?fedora_version} <= 32 - %make_install + %make_install %else %cmake_install %endif @@ -88,7 +88,9 @@ A GlobalProtect VPN client (GUI) for Linux based on OpenConnect and built with Q %{_datadir}/dbus-1/system.d/com.yuezk.qt.GPService.conf %{_datadir}/icons/hicolor/scalable/apps/com.yuezk.qt.gpclient.svg %{_datadir}/metainfo/com.yuezk.qt.gpclient.metainfo.xml +%config %{_sysconfdir}/gpservice/gp.conf +%dir %{_sysconfdir}/gpservice %dir %{_datadir}/icons/hicolor %dir %{_datadir}/icons/hicolor/scalable %dir %{_datadir}/icons/hicolor/scalable/apps diff --git a/scripts/_archive-all.sh b/scripts/_archive-all.sh index 37914a0..ac1efeb 100755 --- a/scripts/_archive-all.sh +++ b/scripts/_archive-all.sh @@ -1,6 +1,6 @@ #!/bin/bash -e -VERSION=$(cat VERSION VERSION_SUFFIX) +VERSION="$(cat VERSION)" rm -rf ./artifacts && mkdir -p ./artifacts/{obs,aur,flatpak} @@ -18,8 +18,8 @@ cp -r ./packaging/obs ./artifacts cp ./artifacts/*.tar.gz ./artifacts/obs/globalprotect-openconnect.tar.gz # Prepare the AUR package -cp ./packaging/aur/PKGBUILD-git ./artifacts/aur/PKGBUILD -cp ./artifacts/*.tar.gz ./artifacts/aur/globalprotect-openconnect.tar.gz +cp ./packaging/aur/PKGBUILD ./artifacts/aur/PKGBUILD +cp ./packaging/aur/gp.install ./artifacts/aur/gp.install # Prepare the flatpak package cp ./packaging/flatpak/com.yuezk.qt.gpclient.yml ./artifacts/flatpak diff --git a/scripts/ppa-publish.sh b/scripts/ppa-publish.sh deleted file mode 100755 index 090debb..0000000 --- a/scripts/ppa-publish.sh +++ /dev/null @@ -1,53 +0,0 @@ -#!/bin/bash -e - -VERSION="$(cat VERSION VERSION_SUFFIX)" -OLD_REVISION="1" - -PPA_REPO="ppa:yuezk/globalprotect-openconnect-snapshot" - -while [[ $# -gt 0 ]]; do - key="$1" - - case $key in - --stable) - PPA_REPO="ppa:yuezk/globalprotect-openconnect" - shift - ;; - "18.04") - DISTRIBUTION="18.04" - DISTRIBUTION_NAME="bionic" - shift - ;; - "20.04") - DISTRIBUTION="20.04" - DISTRIBUTION_NAME="focal" - shift - ;; - "21.04") - DISTRIBUTION="21.04" - DISTRIBUTION_NAME="hirsute" - shift - ;; - "21.10") - DISTRIBUTION="21.10" - DISTRIBUTION_NAME="impish" - shift - ;; - *) - echo "Unkown options $key" - exit 1 - ;; - esac -done - -[ -z $DISTRIBUTION ] && echo "The distribuation is required" && exit 1; - -NEW_REVISION="ppa1~ubuntu${DISTRIBUTION}" - -sed -i"" "1s/${VERSION}-${OLD_REVISION}/${VERSION}-${NEW_REVISION}/;1s/unstable/${DISTRIBUTION_NAME}/" debian/changelog -debmake -debuild -S -sa \ - -k"${PPA_GPG_KEYID}" \ - -p"gpg --batch --passphrase ${PPA_GPG_PASSPHRASE} --pinentry-mode loopback" - -dput $PPA_REPO ../globalprotect-openconnect_${VERSION}-${NEW_REVISION}_source.changes diff --git a/scripts/prepare-packaging.sh b/scripts/prepare-packaging.sh index 0243a7f..a02cba9 100755 --- a/scripts/prepare-packaging.sh +++ b/scripts/prepare-packaging.sh @@ -2,14 +2,13 @@ OLD_VERSION=$(git tag --sort=-v:refname --list "v[0-9]*" | head -n 1 | cut -c 2-) NEW_VERSION="$(cat VERSION)" -FULL_VERSION="$(cat VERSION VERSION_SUFFIX)" HISTORY_ENTRIES=$(git log --format=" * %s" v${OLD_VERSION}.. | cat -n | sort -uk2 | sort -n | cut -f2-) function update_debian_changelog() { local OLD_CHANGELOG=$(cat debian/changelog) cat > debian/changelog <<-EOF - globalprotect-openconnect (${FULL_VERSION}-1) unstable; urgency=medium + globalprotect-openconnect (${NEW_VERSION}-1) unstable; urgency=medium ${HISTORY_ENTRIES} @@ -24,17 +23,24 @@ function update_rpm_changelog() { cat > packaging/obs/globalprotect-openconnect.changes <<-EOF ------------------------------------------------------------------- - $(LC_ALL=en.US date -u "+%a %b %e %T %Z %Y") - k3vinyue@gmail.com - ${FULL_VERSION} + $(LC_ALL=en.US date -u "+%a %b %e %T %Z %Y") - k3vinyue@gmail.com - ${NEW_VERSION} - - Update to ${FULL_VERSION} + - Update to ${NEW_VERSION} ${HISTORY_ENTRIES} ${OLD_CHANGELOG} EOF } +function generate_pkgbuild() { + local commit_id="$(git rev-parse HEAD)" + local version="$(cat VERSION)" + sed -e "s/{COMMIT}/${commit_id}/" -e "s/{VERSION}/${version}/" packaging/aur/PKGBUILD-git.in > packaging/aur/PKGBUILD +} + # Update rpm version -sed -i"" -re "s/(Version:\s+).+/\1${FULL_VERSION}/" packaging/obs/globalprotect-openconnect.spec +sed -i"" -re "s/(Version:\s+).+/\1${NEW_VERSION}/" packaging/obs/globalprotect-openconnect.spec update_rpm_changelog update_debian_changelog +generate_pkgbuild diff --git a/scripts/release.sh b/scripts/release.sh index b62d52f..59fd11e 100755 --- a/scripts/release.sh +++ b/scripts/release.sh @@ -2,9 +2,6 @@ VERSION=$(cat VERSION) -# Clear the VERSION_SUFFIX -cat /dev/null > VERSION_SUFFIX - # Update packaging, e.g., version, changelog, etc. ./scripts/prepare-packaging.sh diff --git a/scripts/snapshot-archive-all.sh b/scripts/snapshot-archive-all.sh index e6df108..71b192c 100755 --- a/scripts/snapshot-archive-all.sh +++ b/scripts/snapshot-archive-all.sh @@ -12,6 +12,3 @@ mv ./artifacts/obs/globalprotect-openconnect-rpmlintrc ./artifacts/obs/globalpro sed -i"" -re "s/(Name:\s+).+/\1globalprotect-openconnect-snapshot/" \ -re "s/(Conflicts:\s+).+/\1globalprotect-openconnect/" \ ./artifacts/obs/globalprotect-openconnect-snapshot.spec - -# Update the AUR package -cp ./packaging/aur/PKGBUILD-git ./artifacts/aur/PKGBUILD \ No newline at end of file diff --git a/scripts/snapshot-version.sh b/scripts/snapshot-version.sh index cf62ac0..99b60b8 100755 --- a/scripts/snapshot-version.sh +++ b/scripts/snapshot-version.sh @@ -1,3 +1,4 @@ #!/bin/bash -e -git describe --tags --match "v$(cat VERSION)" | sed -r -e 's/v([^-]+)-/+snapshot/' -e 's/-/./' > VERSION_SUFFIX +VERSION="v$(cat VERSION)" +git describe --tags --match "${VERSION}" | sed -re 's/^v([^-]+)-([^-]+)-(.+)/\1+\2snapshot.\3/' > VERSION \ No newline at end of file diff --git a/snap/snapcraft.yaml b/snap/snapcraft.yaml index 71c6cd4..4025185 100644 --- a/snap/snapcraft.yaml +++ b/snap/snapcraft.yaml @@ -66,7 +66,7 @@ parts: override-pull: | snapcraftctl pull - VERSION=$(cat VERSION VERSION_SUFFIX) + VERSION=$(cat VERSION) GRADE="stable" if echo "$VERSION" | grep -q "snapshot" diff --git a/version.h.in b/version.h.in index bee27db..eaab018 100644 --- a/version.h.in +++ b/version.h.in @@ -1 +1 @@ -#define VERSION "@GlobalProtect-openconnect_VERSION@@VERSION_SUFFIX@" +#define VERSION "@version@"