diff --git a/CMakeLists.txt b/CMakeLists.txt index ab4bd89..f860d47 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -1,5 +1,5 @@ cmake_minimum_required(VERSION 3.0.0 FATAL_ERROR) -project(platform_folders VERSION 3.0.0 LANGUAGES CXX) +project(platform_folders VERSION 3.1.0 LANGUAGES CXX) # Since it's off, the library will be static by default option(BUILD_SHARED_LIBS "Build shared instead of static." OFF) diff --git a/Makefile b/Makefile deleted file mode 100644 index bf6b328..0000000 --- a/Makefile +++ /dev/null @@ -1,46 +0,0 @@ -ifdef CROSS -CC=$(CROSS)gcc -CXX=$(CROSS)g++ -LD=$(CROSS)ld -AR=$(CROSS)ar -PKG_CONFIG=$(CROSS)pkg-config -endif - -BASE_LIBS= -BASE_CFLAGS=-c -g -O2 -Wall -Wextra -pedantic-errors - -#The files should compile on both C++03 and C++11 -ifdef TESTCPP11 -BASE_CFLAGS+= -std=c++11 -else -BASE_CFLAGS+= -std=c++03 -endif - -#This is used to detect Mac because Mac needs CoreServices for linking -ifneq ($(OS),Windows_NT) -UNAME := $(shell uname -s) -ifeq ($(UNAME),Darwin) -BASE_LIBS+= -framework CoreServices -endif -endif - -PROGRAMNAME=platform_folders - -O_FILES=${PROGRAMNAME}.o sago/platform_folders.o - -total: ${PROGRAMNAME}.out - -clean: - rm -f */*.o *.o *.P */*.P ${PROGRAMNAME}.out - -${PROGRAMNAME}.out: $(O_FILES) - $(CXX) -O -o ${PROGRAMNAME}.out $(O_FILES) $(BASE_LIBS) - -%.o : %.cpp - $(CXX) -MD ${BASE_CFLAGS} -o $@ $< - @mkdir -p `dirname .$(CROSS)deps/$*.P` && cp $*.d .$(CROSS)deps/$*.P; \ - sed -e 's/#.*//' -e 's/^[^:]*: *//' -e 's/ *\\$$//' \ - -e '/^$$/ d' -e 's/$$/ :/' < $*.d >> .$(CROSS)deps/$*.P; \ - rm -f $*.d - --include .$(CROSS)deps/*.P diff --git a/README.md b/README.md index 1d28fbc..8ffdc0d 100644 --- a/README.md +++ b/README.md @@ -1,5 +1,5 @@ -# PlatformFolders [![Build Status](https://travis-ci.org/sago007/PlatformFolders.svg?branch=master)](https://travis-ci.org/sago007/PlatformFolders) [![license](https://img.shields.io/github/license/sago007/PlatformFolders.svg)](https://raw.githubusercontent.com/sago007/PlatformFolders/master/LICENSE) [![Join the chat at https://gitter.im/PlatformFolders/Lobby](https://badges.gitter.im/PlatformFolders/Lobby.svg)](https://gitter.im/PlatformFolders/Lobby?utm_source=badge&utm_medium=badge&utm_campaign=pr-badge&utm_content=badge) [![Codacy Badge](https://api.codacy.com/project/badge/Grade/729e36adcf5c4523bd136de1b33441cb)](https://www.codacy.com/app/github_43/PlatformFolders?utm_source=github.com&utm_medium=referral&utm_content=sago007/PlatformFolders&utm_campaign=Badge_Grade) -A C++ library to look for special directories like "My Documents" and "%APPDATA%" so that you do not need to write Linux, Windows or Mac OS X specific code +# PlatformFolders [![Build Status](https://travis-ci.org/sago007/PlatformFolders.svg?branch=master)](https://travis-ci.org/sago007/PlatformFolders) [![license](https://img.shields.io/github/license/sago007/PlatformFolders.svg)](https://raw.githubusercontent.com/sago007/PlatformFolders/master/LICENSE) +A C++ library to look for special directories like "My Documents" and "%APPDATA%" so that you do not need to write Linux, Windows and Mac OS X specific code Can be found at: https://github.com/sago007/PlatformFolders @@ -40,11 +40,22 @@ Uses the deprecated FSFindFolder (there is no C++ alternative). It requires "-fr # Usage Copy "sago/platform_files.cpp" and "sago/platform_fildes.h" to your program and make sure that the cpp file is compiled and linked. +It is also possible to compile and it like: +``` +mkdir -p build +cd build +cmake .. +make +``` +Just be aware that Mac OS X requires "-framework CoreServices" during linking no matter the choice. + # Hello World This sample program gets all folders from the system: ``` #include +#include +#include #include "sago/platform_folders.h" using std::cout; @@ -108,8 +119,14 @@ Download: /Users/poul/Downloads Save Games 1: /Users/poul/Library/Application Support ``` +# C++ support +Versions up to 3.X.X should compile with any C++98 compiler. +Versions from 4.0.0 and up requires a C++11 compatible compiler. + +The aim is to always support the default C++ compiler on the oldest supported version of Ubuntu. This is a very basic library and it is not supposed to force you to upgrade. + # Encoding -From version 3.0 UTF-8 is always used on Windows and will also be the default in almost any other system. +From version 3.0 UTF-8 is always used on Windows and will also be the default on almost any other system. Before version 3.0 Windows used ANSI encoding. Microsoft's default choice of UTF-16 is not compatible with platform independent code. Although the user may use an characters they want I recommend, that the program should not have non ASCII characters in the source code itself. diff --git a/compile_test.sh b/compile_test.sh deleted file mode 100755 index 56ffb1e..0000000 --- a/compile_test.sh +++ /dev/null @@ -1,12 +0,0 @@ -#! /bin/bash -set -e -#This script will attempt to compile with C++11, cross compile to windows with C++11, cross compile to windows with C++03, compile with C++03 -make clean -make TESTCPP11=1 -make clean -make CROSS=i686-w64-mingw32.static- TESTCPP11=1 -make clean -make CROSS=i686-w64-mingw32.static- -mv platform_folders.out platform_folders.exe -make clean -make diff --git a/sago/platform_folders.cpp b/sago/platform_folders.cpp index 004ceac..ddb63a9 100644 --- a/sago/platform_folders.cpp +++ b/sago/platform_folders.cpp @@ -30,15 +30,13 @@ SOFTWARE. #include #include #include -#include +#include #include #if defined(_WIN32) #include #include -#define strtok_r strtok_s - static std::string win32_utf16_to_utf8(const wchar_t* wstr) { std::string res; @@ -52,7 +50,7 @@ static std::string win32_utf16_to_utf8(const wchar_t* wstr) } if (actualSize == 0) { // WideCharToMultiByte return 0 for errors. - std::string errorMsg = "UTF16 to UTF8 failed with error code: " + GetLastError(); + const std::string errorMsg = "UTF16 to UTF8 failed with error code: " + GetLastError(); throw std::runtime_error(errorMsg.c_str()); } return res; @@ -101,12 +99,14 @@ static std::string GetMacFolder(OSType folderType, const char* errorMsg) { #include #include #include +// For strlen and strtok +#include //Typically Linux. For easy reading the comments will just say Linux but should work with most *nixes static void throwOnRelative(const char* envName, const char* envValue) { if (envValue[0] != '/') { char buffer[200]; - snprintf(buffer, sizeof(buffer), "Environment \"%s\" does not start with an '/'. XDG specifies that the value must be absolute. The current value is: \"%s\"", envName, envValue); + std::snprintf(buffer, sizeof(buffer), "Environment \"%s\" does not start with an '/'. XDG specifies that the value must be absolute. The current value is: \"%s\"", envName, envValue); throw std::runtime_error(buffer); } } @@ -120,7 +120,7 @@ static void throwOnRelative(const char* envName, const char* envValue) { static std::string getHome() { std::string res; int uid = getuid(); - const char* homeEnv = getenv("HOME"); + const char* homeEnv = std::getenv("HOME"); if ( uid != 0 && homeEnv) { //We only acknowlegde HOME if not root. res = homeEnv; @@ -140,7 +140,7 @@ static std::string getHome() { static std::string getLinuxFolderDefault(const char* envName, const char* defaultRelativePath) { std::string res; - const char* tempRes = getenv(envName); + const char* tempRes = std::getenv(envName); if (tempRes) { throwOnRelative(envName, tempRes); res = tempRes; @@ -151,9 +151,8 @@ static std::string getLinuxFolderDefault(const char* envName, const char* defaul } static void appendExtraFoldersTokenizer(const char* envName, const char* envValue, std::vector& folders) { - std::vector buffer(envValue, envValue + strlen(envValue) + 1); - char *saveptr; - const char* p = strtok_r ( &buffer[0], ":", &saveptr); + std::vector buffer(envValue, envValue + std::strlen(envValue) + 1); + char* p = std::strtok ( &buffer[0], ":"); while (p != NULL) { if (p[0] == '/') { folders.push_back(p); @@ -163,12 +162,12 @@ static void appendExtraFoldersTokenizer(const char* envName, const char* envValu //The XDG documentation indicates that the folder should be ignored but that the program should continue. std::cerr << "Skipping path \"" << p << "\" in \"" << envName << "\" because it does not start with a \"/\"\n"; } - p = strtok_r (NULL, ":", &saveptr); + p = std::strtok (NULL, ":"); } } static void appendExtraFolders(const char* envName, const char* defaultValue, std::vector& folders) { - const char* envValue = getenv(envName); + const char* envValue = std::getenv(envName); if (!envValue) { envValue = defaultValue; }