diff --git a/.github/dependabot.yml b/.github/dependabot.yml deleted file mode 100644 index f6dab30a..00000000 --- a/.github/dependabot.yml +++ /dev/null @@ -1,12 +0,0 @@ -# See: https://docs.github.com/en/github/administering-a-repository/configuration-options-for-dependency-updates#about-the-dependabotyml-file -version: 2 - -updates: - # Configure check for outdated GitHub Actions actions in workflows. - # See: https://docs.github.com/en/github/administering-a-repository/keeping-your-actions-up-to-date-with-dependabot - - package-ecosystem: github-actions - directory: / # Check the repository's workflows under /.github/workflows/ - labels: - - "topic: infrastructure" - schedule: - interval: daily diff --git a/.github/workflows/sync-labels.yml b/.github/workflows/sync-labels.yml deleted file mode 100644 index 4ea57559..00000000 --- a/.github/workflows/sync-labels.yml +++ /dev/null @@ -1,138 +0,0 @@ -# Source: https://github.com/arduino/tooling-project-assets/blob/main/workflow-templates/sync-labels.md -name: Sync Labels - -# See: https://docs.github.com/en/actions/reference/events-that-trigger-workflows -on: - push: - paths: - - ".github/workflows/sync-labels.ya?ml" - - ".github/label-configuration-files/*.ya?ml" - pull_request: - paths: - - ".github/workflows/sync-labels.ya?ml" - - ".github/label-configuration-files/*.ya?ml" - schedule: - # Run daily at 8 AM UTC to sync with changes to shared label configurations. - - cron: "0 8 * * *" - workflow_dispatch: - repository_dispatch: - -env: - CONFIGURATIONS_FOLDER: .github/label-configuration-files - CONFIGURATIONS_ARTIFACT: label-configuration-files - -jobs: - check: - runs-on: ubuntu-latest - - steps: - - name: Checkout repository - uses: actions/checkout@v3 - - - name: Download JSON schema for labels configuration file - id: download-schema - uses: carlosperate/download-file-action@v1 - with: - file-url: https://raw.githubusercontent.com/arduino/tooling-project-assets/main/workflow-templates/assets/sync-labels/arduino-tooling-gh-label-configuration-schema.json - location: ${{ runner.temp }}/label-configuration-schema - - - name: Install JSON schema validator - run: | - sudo npm install \ - --global \ - ajv-cli \ - ajv-formats - - - name: Validate local labels configuration - run: | - # See: https://github.com/ajv-validator/ajv-cli#readme - ajv validate \ - --all-errors \ - -c ajv-formats \ - -s "${{ steps.download-schema.outputs.file-path }}" \ - -d "${{ env.CONFIGURATIONS_FOLDER }}/*.{yml,yaml}" - - download: - needs: check - runs-on: ubuntu-latest - - strategy: - matrix: - filename: - # Filenames of the shared configurations to apply to the repository in addition to the local configuration. - # https://github.com/arduino/tooling-project-assets/blob/main/workflow-templates/assets/sync-labels - - universal.yml - - steps: - - name: Download - uses: carlosperate/download-file-action@v1 - with: - file-url: https://raw.githubusercontent.com/arduino/tooling-project-assets/main/workflow-templates/assets/sync-labels/${{ matrix.filename }} - - - name: Pass configuration files to next job via workflow artifact - uses: actions/upload-artifact@v2 - with: - path: | - *.yaml - *.yml - if-no-files-found: error - name: ${{ env.CONFIGURATIONS_ARTIFACT }} - - sync: - needs: download - runs-on: ubuntu-latest - - steps: - - name: Set environment variables - run: | - # See: https://docs.github.com/en/actions/reference/workflow-commands-for-github-actions#setting-an-environment-variable - echo "MERGED_CONFIGURATION_PATH=${{ runner.temp }}/labels.yml" >> "$GITHUB_ENV" - - - name: Determine whether to dry run - id: dry-run - if: > - github.event_name == 'pull_request' || - ( - ( - github.event_name == 'push' || - github.event_name == 'workflow_dispatch' - ) && - github.ref != format('refs/heads/{0}', github.event.repository.default_branch) - ) - run: | - # Use of this flag in the github-label-sync command will cause it to only check the validity of the - # configuration. - echo "::set-output name=flag::--dry-run" - - - name: Checkout repository - uses: actions/checkout@v3 - - - name: Download configuration files artifact - uses: actions/download-artifact@v2 - with: - name: ${{ env.CONFIGURATIONS_ARTIFACT }} - path: ${{ env.CONFIGURATIONS_FOLDER }} - - - name: Remove unneeded artifact - uses: geekyeggo/delete-artifact@v1 - with: - name: ${{ env.CONFIGURATIONS_ARTIFACT }} - - - name: Merge label configuration files - run: | - # Merge all configuration files - shopt -s extglob - cat "${{ env.CONFIGURATIONS_FOLDER }}"/*.@(yml|yaml) > "${{ env.MERGED_CONFIGURATION_PATH }}" - - - name: Install github-label-sync - run: sudo npm install --global github-label-sync - - - name: Sync labels - env: - GITHUB_ACCESS_TOKEN: ${{ secrets.GITHUB_TOKEN }} - run: | - # See: https://github.com/Financial-Times/github-label-sync - github-label-sync \ - --labels "${{ env.MERGED_CONFIGURATION_PATH }}" \ - ${{ steps.dry-run.outputs.flag }} \ - ${{ github.repository }} diff --git a/.gitignore b/.gitignore index a464c416..1744b06e 100644 --- a/.gitignore +++ b/.gitignore @@ -42,4 +42,5 @@ core # .vs -.vscode + +src - 副本 \ No newline at end of file diff --git a/.vscode/c_cpp_properties.json b/.vscode/c_cpp_properties.json new file mode 100644 index 00000000..974e0854 --- /dev/null +++ b/.vscode/c_cpp_properties.json @@ -0,0 +1,55 @@ +{ + "configurations": [ + { + "name": "avr", + "includePath": [ + "${workspaceFolder}/src", + "${LOCALAPPDATA}/Arduino15/packages/arduino/hardware/avr/1.8.6/cores/arduino", + "${LOCALAPPDATA}/Arduino15/packages/arduino/hardware/avr/1.8.6/variants/mega", + "${LOCALAPPDATA}/Arduino15/packages/arduino/tools/avr-gcc/7.3.0-atmel3.6.1-arduino7/avr/include" + ], + "defines": [ + "F_CPU=16000000L", + "ARDUINO_AVR_MEGA2560", + "__AVR_ATmega2560__", + "ARDUINO_ARCH_AVR=1", + "VSCODE" + ], + "compilerPath": "${LOCALAPPDATA}/Arduino15/packages/arduino/tools/avr-gcc/7.3.0-atmel3.6.1-arduino7/bin/avr-g++.exe", + "cStandard": "c11", + "cppStandard": "c++17" + }, + { + "name": "sam", + "includePath": [ + "${workspaceFolder}/src", + "${LOCALAPPDATA}/Arduino15/packages/arduino/hardware/sam/1.6.12/**", + "${LOCALAPPDATA}/Arduino15/packages/arduino/tools/arm-none-eabi-gcc/4.8.3-2014q1/arm-none-eabi/include", + "${LOCALAPPDATA}/Arduino15/packages/arduino/tools/arm-none-eabi-gcc/4.8.3-2014q1/lib/gcc/arm-none-eabi/4.8.3/include-fixed" + ], + "defines": [ + "F_CPU=84000000L", + "ARDUINO_SAM_DUE", + "ARDUINO_ARCH_SAM=1", + "__SAM3X8E__=1", + "VSCODE" + ], + "compilerPath": "${LOCALAPPDATA}/Arduino15/packages/arduino/tools/arm-none-eabi-gcc/4.8.3-2014q1/bin/arm-none-eabi-g++.exe", + "cStandard": "c11", + "cppStandard": "c++11" + }, + { + "name": "esp32", + "includePath": [ + "${workspaceFolder}/src", + ], + "defines": [ + "ARDUINO_ARCH_ESP32=1" + ], + "compilerPath": "${LOCALAPPDATA}/Arduino15/packages/esp32/tools/esp-xs3/2302/bin/xtensa-esp32s3-elf-gcc.exe", + "cStandard": "c11", + "cppStandard": "c++20" + } + ], + "version": 4 +} \ No newline at end of file diff --git a/.vscode/settings.json b/.vscode/settings.json new file mode 100644 index 00000000..0c3037ed --- /dev/null +++ b/.vscode/settings.json @@ -0,0 +1,103 @@ +{ + "files.associations": { + "memory": "cpp", + "xtr1common": "cpp", + "char_traits": "cpp", + "type_traits": "cpp", + "xmemory": "cpp", + "functional": "cpp", + "iterator_base": "cpp", + "limits": "cpp", + "new": "cpp", + "support": "cpp", + "utility": "cpp", + "cstddef": "cpp", + "xstddef": "cpp", + "basic_definitions": "cpp", + "algorithm": "cpp", + "valarray": "cpp", + "xutility": "cpp", + "climits": "cpp", + "random": "cpp", + "istream": "cpp", + "bitset": "cpp", + "complex": "cpp", + "iomanip": "cpp", + "iosfwd": "cpp", + "iostream": "cpp", + "istream_helpers": "cpp", + "iterator": "cpp", + "serstream": "cpp", + "sstream": "cpp", + "string_iostream": "cpp", + "ostream": "cpp", + "chrono": "cpp", + "ratio": "cpp", + "cstdint": "cpp", + "__config": "cpp", + "cstdlib": "cpp", + "*.tcc": "cpp", + "unordered_map": "cpp", + "cmath": "cpp", + "array": "cpp", + "tuple": "cpp", + "deque": "cpp", + "list": "cpp", + "vector": "cpp", + "cwctype": "cpp", + "cwchar": "cpp", + "streambuf": "cpp", + "ios": "cpp", + "exception": "cpp", + "typeinfo": "cpp", + "initializer_list": "cpp", + "stdexcept": "cpp", + "func_exception": "cpp", + "string": "cpp", + "cstdio": "cpp", + "ostream_helpers": "cpp", + "locale": "cpp", + "cctype": "cpp", + "new2": "cpp", + "cstring": "cpp", + "ctime": "cpp", + "numeric": "cpp", + "associative_base": "cpp", + "stack": "cpp", + "atomic": "cpp", + "clocale": "cpp", + "cstdarg": "cpp", + "memory_resource": "cpp", + "optional": "cpp", + "string_view": "cpp", + "system_error": "cpp", + "fstream": "cpp", + "cinttypes": "cpp", + "queue": "cpp", + "map": "cpp", + "set": "cpp", + "cerrno": "cpp", + "codecvt": "cpp", + "dynarray": "cpp", + "stdio.h": "cpp", + "printf.h": "cpp", + "features.h": "cpp", + "file.h": "cpp", + "locale.h": "cpp", + "cpp_standard_library.h": "cpp", + "langinfo.h": "cpp", + "errno.h": "cpp", + "printf_buffer.h": "cpp", + "stdint.h": "cpp", + "stdbool.h": "cpp", + "cdefs.h": "cpp", + "types.h": "cpp", + "string.h": "cpp", + "bit": "cpp", + "libc-symbols.h": "cpp", + "unordered_set": "cpp", + "span": "cpp", + "concepts": "cpp", + "numbers": "cpp" + } +} \ No newline at end of file diff --git a/README.md b/README.md index 2bc784ce..b0c7933f 100644 --- a/README.md +++ b/README.md @@ -1,98 +1,38 @@ -# ArduinoSTL - -This is an implementation of a C++ standard library packaged as an Arduino library. The library supports teaching my CS-11M class by adding key C++ features into the Arduino environment. - -The library is ported from uClibc++: - -http://git.uclibc.org/uClibc++ - -With a streams implementation from Andy Brown's Arduino Library: - -http://andybrown.me.uk/2011/01/15/the-standard-template-library-stl-for-avr-with-c-streams/ - - -## Using printf() and scanf() -The ArduinoSTL header file contains code to bind a serial port of your choice to -the stdio primitives. This happens automatically but the user must still call -Serial.begin() - -```c++ -#include - -void setup() { - Serial.begin(9600); - printf("Hello World\n"); -} -``` - -## Using ```cin``` an ```cout``` -When you include this header file you automatically get cin and cout based on ```Serial```. See below for how to specify your own device. Here's an example sketch using ```cin``` and ```cout``` . - -```c++ -#include - -using namespace std; - -void setup() { - Serial.begin(9600); - cout << "Feed me an integers." << endl; -} - -void loop() { - int foo; - if (cin >> foo) { - cout << "You fed me " << foo << endl; - }else{ - cin.clear(); - cin.ignore(); - } -} -``` -## Changing the Serial Port -You can change what serial port that ```cin```, ```cout``` and ```printf()``` use. You can use built-in serial ports (e.g. ```Serial1``` on Leonardo) or you can use software serial ports that implement ```Stream```. - -### Using a Built-in Port -In ```src/ArduinoSTL.cpp``` change the value of ```ARDUINOSTL_DEFAULT_SERIAL```. Leave the other defaults uncommented. - -### Using a SoftwareSerial port. -Set ```ARDUINO_DEFAULT_SERAL``` to ```NULL```. Comment out the other defaults. - -Here's an example sketch that uses SofwareSerial: - -```c++ -#include -#include - -SoftwareSerial mySerial(0, 1); - -namespace std { - ohserialstream cout(mySerial); - ihserialstream cin(mySerial); -} - -void setup() { - mySerial.begin(9600); - ArduinoSTL_Serial.connect(mySerial); -} -``` - -## Avoiding Instantiation of ```cin``` and ```cout``` -Comment out ```ARDUINOSTL_DEFAULT_CIN_COUT``` and nothing will be instantiated. You must comment out this flag if you intend to select a non-default serial port. There's no appreciable overhead for using ```printf()``` so you cannot currently avoid initializaing it. - -## Known Issues - -Printing of floats and doubles using ```cout``` ignores format specifiers. - -uClibc seems to be fairly complete. Strings and vectors both work, even with the limited amount of heap available to Arduino. The uClibc++ status page can be found here: - -https://cxx.uclibc.org/status.html - -Always use the latest Arduino IDE. This library uses the Arduino IDE Library Specification rev.2.1 with features only available on Arduino 1.6.10 and higher. The specification can be found here: - -https://github.com/arduino/Arduino/wiki/Arduino-IDE-1.5:-Library-specification - -## License - -The uClibc++ library is licensed under the LGPL. This project adopts the LGPL to be compatible with the bulk of the code that it uses. Unless otherwise noted all code is licensed under the LGPL. There's one exception: - - - src/serstream is licensed under the BSD license according to Andy Brown's wishes here: http://andybrown.me.uk/terms-and-conditions/ +因[原版ArduinoSTL](https://github.com/mike-matera/ArduinoSTL)作者长期不更新(上次更新是2022年),本人将此分支发布到Arduino公开库,改名为Cpp_Standard_Library以示区分。 + +本库试图在Arduino上实现C++11~17标准库(STL)的大部分功能。除了ArduinoSTL以外,本库部分功能实现还参考了GCC(为主)和boost。因为是按照STL做的接口,所以不需要另外撰写文档,你可以参考任何一个权威的STL文档。除非另有说明,否则本库的使用方法应该是一样的,如果不一样那应该就是个bug,欢迎提交Issue。 + +如果你需要某些标准库中应有而本库中尚未提供的功能,也欢迎提交Issue,作者将会优先为你实现。 + +支持以下架构: +- AVR,但要求C++17:需要更改`%LOCALAPPDATA%\Arduino15\packages\arduino\hardware\avr\*.*.*\platform.txt`中的`-std=gnu++11`为`-std=gnu++17` +- SAM +- ESP32(by Espressif Systems, not Arduino) + +对于SAM和ESP32架构,如欲使用C++标准异常处理和运行时类型识别(RTTI, typeid),还需要确保编译选项包含-fexceptions且不含-fno-rtti。AVR架构不支持异常处理,设置-fexceptions或使用try关键词将导致未定义行为。 + +在包含任何C++标准头文件之前,必须先包含`Cpp_Standard_Library.h`。这是对 Arduino IDE 的提示,告诉编译器必须要将本库纳入编译流程。 +# 招牌功能(不限于此) +- ` fill_n shuffle` +- ` chrono::duration` +- ` log2` +- `` 注意C++20之前并不真正支持concept。此头文件允许你以 constexpr bool 变量模板(C++17)或函数模板(C++11)形式访问C++标准concepts。 +- `` 曾经有望进入C++标准的废案。虽然最终没能进入,但作为`array`和`vector`的中间类型非常有用。 +- `` 非标准行为:调用空对象时不做任何事。这是因为标准行为是应当抛出异常,但Arduino不支持异常。如果希望调用空对象时不做任何事,则可无需判断对象是否为空而直接调用。 +- ` cin cout endl` 使用`Serial`实现标准输入输出流。但是,使用前仍必须手动`Serial.begin`以设置波特率。不应在`setup`函数之前的全局变量初始化阶段使用`Serial`,因为在`setup`被调用之前无法保证`Serial`已完成初始化,此时使用`Serial`是未定义行为。此外测试发现,对于SAM架构,串口刚完成初始化后可能会发送一些随机字节,这似乎是硬件设计缺陷使然,软件层面无法解决,接收端必须要考虑到这个问题。 +- `` +- ` unique_ptr make_unique shared_ptr make_unique_for_overwrite` +- `` +- `` `ArduinoUrng`是Arduino平台特定的`UniformRandomNumberGenerator`,可用于`shuffle`,属于软件伪随机生成器,需要设置随机种子。ESP32和SAM架构还额外支持`TrueUrng`,是硬件真随机生成器,不支持设置种子。 +- `` +- `` +- `` +- `` +- `` +- `` +- `` +- `std::begin std::end` +- 如果编译器随附了某些重名的标准库功能,将优先使用随附的版本。编译器可能还随附了本库未提供的其它标准库功能,那些功能也不会与本库冲突。 +- (AVR不支持)C++标准异常处理和RTTI。要使用此功能,请确保编译选项包含-fexceptions且不含-fno-rtti。异常处理代码依赖RTTI,因此不能在关闭RTTI的情况下使用异常处理。 + +安装后记得查看示例项目! \ No newline at end of file diff --git a/examples/Functional/Functional.ino b/examples/Functional/Functional.ino new file mode 100644 index 00000000..7eb20413 --- /dev/null +++ b/examples/Functional/Functional.ino @@ -0,0 +1,55 @@ +#include +//演示多个标准库的功能,无可展示的运行时效果 +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +std::map &&) const>> ListeningPorts; +std::unordered_map &&) const>> UListeningPorts; +std::queue> MessageQueue; +std::unordered_set *> IdleTasks; +std::set PointerSet; +void Translate(std::chrono::hours H) { + std::cout << std::chrono::duration_cast(H + H).count() << std::endl; +} +std::move_only_function FF; +void setup() { + std::unique_ptr US = std::make_unique_for_overwrite(10); + std::shared_ptr SSS; + std::fill_n(US.get(), 10, std::chrono::hours(1)); + std::chrono::hours H = US[5]; + FF = [H]() { + Translate(H); + }; + std::dynarray D(std::log2(1024)); + std::unordered_map> UIF; + bool A = IdleTasks.contains(nullptr); + bool B = ListeningPorts.contains(0); + bool C = UListeningPorts.contains(0); + std::span SpanBool(&A,1); + UIF[1] = []() {}; + std::queue> QF; + QF.emplace([]() {}); + QF.pop(); +#if __cpp_exceptions + try { + throw 0; + } catch (int E) {} +#endif +#ifdef __cpp_deduction_guides + std::move_only_function DeductionTest([]() {}); +#endif + PointerSet.contains(nullptr); +} +void loop() { + FF(); +} \ No newline at end of file diff --git a/examples/RandomShuffle/RandomShuffle.ino b/examples/RandomShuffle/RandomShuffle.ino new file mode 100644 index 00000000..a30e8d88 --- /dev/null +++ b/examples/RandomShuffle/RandomShuffle.ino @@ -0,0 +1,61 @@ +//此示例需要使用串口监视器呈现。先生成一个原始数组0123456789,然后根据用户输入的随机种子,不断产生随机排序。 +#include +#include +#include +#include +#include +template +struct MakeArray {}; +template +struct MakeArray> { + static size_t value[sizeof...(V)]; +}; +template +size_t MakeArray>::value[sizeof...(V)] = { V... }; +size_t (&Array)[10] = MakeArray>::value; +void setup() { + Serial.begin(9600); + std::cout << "原始数组:"; + for (size_t A : Array) + std::cout << A; + //很多平台并不原生支持uint64_t,但本库仍能输出 + for (uint64_t A : Array) + std::cout << A; + std::cout << std::endl; +} +void loop() { + static uint32_t RandomSeed; +#ifdef ARDUINO_ARCH_AVR + //非标准行为:ArduinoUrng是Arduino平台专用的随机生成器。你也可以使用标准库提供的mt19937,但它占用了太多内存,不建议使用。 + constexpr std::ArduinoUrng Urng; + std::cout << "输入随机种子(非数字的输入将被忽略):"; + std::cin >> RandomSeed; + std::ArduinoUrng::seed(RandomSeed); +#else + //SAM和ESP32架构额外提供真随机生成器,不需要随机种子 + constexpr std::TrueUrng Urng; + std::cout << "输入任意字符以生成下一个乱序:"; + std::cin >> RandomSeed; +#endif + + // 清除错误标志位。必须紧贴ignore之前,因为不先清除错误状态ignore就不会生效。 + std::cin.clear(); + + // 丢弃错误输入。必须在获取RandomSeed之后,否则第一次输入会被忽略 + std::cin.ignore(std::numeric_limits::max(), '\n'); + + std::cout << RandomSeed << std::endl; + std::shuffle(std::begin(Array), std::end(Array), Urng); + std::cout << "随机乱序:"; + for (size_t A : Array) + std::cout << A; + std::cout << std::endl; +#ifdef __cpp_exceptions + //此段仅用于展示异常处理,对本示例主线逻辑无意义。必须在编译选项中启用-fexceptions并禁用-fno-rtti才能使本段生效。AVR不支持异常处理。 + try { + throw 0; + } catch (...) { + std::cout << "成功捕获异常" << std::endl; + } +#endif +} \ No newline at end of file diff --git a/keywords.txt b/keywords.txt deleted file mode 100644 index dc4e07ab..00000000 --- a/keywords.txt +++ /dev/null @@ -1,4 +0,0 @@ -cin KEYWORD1 -cout KEYWORD1 -printf KEYWORD1 -scanf KEYWORD1 diff --git a/library.properties b/library.properties index 977edffd..ee1f776b 100644 --- a/library.properties +++ b/library.properties @@ -1,10 +1,10 @@ -name=ArduinoSTL -version=1.3.3 -author=Mike Matera , Chris Johnson , Arduino -maintainer=Mike Matera -sentence=A port of uClibc++ Arduino library. -paragraph=This library includes important C++ functions, including cout and cin, printf and scanf. It also includes STL containers like vector and algorithm. +name=Cpp_Standard_Library +version=3.1.0 +author=埃博拉酱 , Mike Matera , Chris Johnson , Arduino +maintainer=埃博拉酱 +sentence=将C++标准库移植到 Arduino。支持C++11~17。Porting the C++ standard library to Arduino. Support C++11~17. +paragraph=将你熟悉的C++标准库功能丝滑迁移到Arduino!将串口作为cin和cout的基础,并支持 avr esp32 sam 三大架构。Migrate your familiar C++ standard library features smoothly to Arduino! The serial port is used as the basis of cin and cout, and supports the three architectures of avr esp32 sam. category=Other -url=https://github.com/mike-matera/ArduinoSTL -architectures=avr,megaavr -includes=ArduinoSTL.h +url=https://github.com/Silver-Fang/Cpp_Standard_Library +architectures=avr,sam,esp32 +includes=Cpp_Standard_Library.h diff --git a/src/Arduino/HardwareSerial.cpp b/src/Arduino/HardwareSerial.cpp new file mode 100644 index 00000000..fdd384ae --- /dev/null +++ b/src/Arduino/HardwareSerial.cpp @@ -0,0 +1,5 @@ +#ifdef ARDUINO_ARCH_SAM +#include +void HardwareSerial::begin(unsigned long) {} +void HardwareSerial::end() {} +#endif \ No newline at end of file diff --git a/src/ArduinoSTL.cpp b/src/ArduinoSTL.cpp deleted file mode 100644 index 4208aa6e..00000000 --- a/src/ArduinoSTL.cpp +++ /dev/null @@ -1,80 +0,0 @@ -#include "ArduinoSTL.h" -#include - -// -// Configuration Help -// -// If you're using a serial port that's statically declared somewhere in -// Arduino (e.g. Serial1 on Leonardo) -// 1. Set ARDUINOSTL_SERIAL_DEVICE to your device -// 2. Uncomment the ARDUINOSTL_DEFAULT_CIN_COUT flag. -// -// If you're using a sofware serial port: -// 1. Set ARDUINOSTL_DEFAULT_SERIAL to NULL -// 2. Comment out ARDUINOSTL_DEFAULT_CIN_COUT -// Your sketch must contain delarations of cin and cout, and a call to -// ArduinoSTL_serial.connect(). -// - -#define ARDUINOSTL_DEFAULT_SERIAL Serial -#define ARDUINOSTL_DEFAULT_CIN_COUT - -using namespace std; - -#ifdef ARDUINOSTL_DEFAULT_CIN_COUT -// Create cout and cin.. there doesn't seem to be a way -// to control what serial device at runtime. Grr. -namespace std -{ - ohserialstream cout(ARDUINOSTL_DEFAULT_SERIAL); - ihserialstream cin(ARDUINOSTL_DEFAULT_SERIAL); -} -#endif // ARDUINOSTL_DEFAULT_CIN_COUT - -/* - * Implementation of printf() is highly libc dependent. - * - * This implementation is tested on: - * - * ARDUINO_ARCH_AVR (Classic Arduinos) - Working - * TEENSYDUINO (ARM-based Teensy) - cin/cout work, printf doesn't - * ARDUINO_ARCH_* - ARMs are probably the same as above. - */ -#if defined(ARDUINO_ARCH_AVR) - -ArduinoSTL_STDIO ArduinoSTL_Serial(ARDUINOSTL_DEFAULT_SERIAL); - -// arduino_putchar(char, FILE*) -// Output a single character to the serial port. -// returns: 0 on success, 1 on error -// note: -// To maintain serial port compatibility this function -// automatically addes a \r when it sees a \n -// -static int arduino_putchar(char c, FILE* f) { - Stream *uart = ArduinoSTL_Serial.getUart(); - if (c == '\n') uart->write('\r'); - return uart->write(c) == 1? 0 : 1; -} - -// arduino_getchar(FILE*) -// Take a character from the serial port. This function -// must block until a character is ready. -// returns: The character or -1 on a read error -// -static int arduino_getchar(FILE *f) { - Stream *uart = ArduinoSTL_Serial.getUart(); - while (! uart->available()) { /* wait */ } - return uart->read(); -} - -void ArduinoSTL_STDIO::connect(Stream *u) { - if (file != NULL) - free (file); - uart = u; - file = fdevopen(arduino_putchar, arduino_getchar); -} - -#else -#warning "printf() will not be functional on this platform." -#endif diff --git a/src/ArduinoSTL.h b/src/ArduinoSTL.h deleted file mode 100644 index d692afa4..00000000 --- a/src/ArduinoSTL.h +++ /dev/null @@ -1,56 +0,0 @@ -/*--------------------- - * - * ArduinoSTL Core Library - * - * This header has some glue to make STL and Streams work from a sketch. - * - */ - -#ifndef ARDUINOSTL_M_H -#define ARDUINOSTL_M_H - -#include -#include "serstream" - -// Create cout and cin.. there doesn't seem to be a way -// to control what serial device at runtime. Grr. -namespace std -{ - extern ohserialstream cout; - extern ihserialstream cin; -} - -#if defined(ARDUINO_ARCH_AVR) - -class ArduinoSTL_STDIO { -public: - // Initialize STDIO using a pointer to whatever Serial is. - // Serial.begin() must be called at some point. - ArduinoSTL_STDIO(Stream *u) : file(NULL) { - connect(u); - } - - ArduinoSTL_STDIO(Stream &u) : file(NULL) { - connect(u); - } - - Stream *getUart() { - return uart; - } - - void connect(Stream *u); - - inline void connect(Stream &u) { - connect(static_cast(&u)); - } - -private: - Stream *uart; - FILE *file; -}; - -extern ArduinoSTL_STDIO ArduinoSTL_Serial; - -#endif // ARDUINO_ARCH_AVR - -#endif // ARDUINOSTL_M_H diff --git a/src/Cpp_Standard_Library.h b/src/Cpp_Standard_Library.h new file mode 100644 index 00000000..e4c12ba8 --- /dev/null +++ b/src/Cpp_Standard_Library.h @@ -0,0 +1,18 @@ +#pragma once +// 此头文件用于标识本库已被包含,并提示编译器应当编译本库中的源文件。请按需包含具体的功能头文件。 +#define _DEBUG 1 +#define __STDCPP_DEFAULT_NEW_ALIGNMENT__ (size_t)16 +#define __cpp_sized_deallocation 1 +#define _GLIBCXX_ATOMIC_BUILTINS + +//Arduino不支持#include_next,只能用这种魔法实现包含官方标准库 +#ifdef ARDUINO_ARCH_AVR +#define _CSL_Official(Header) +#define _CSL_OfficialC(Header) +#else +#define _CSL_Official(Header) +#define _CSL_OfficialC(Header) <_ansi.h/../../include/Header> +#define _CSL_OfficialB(Header) +#endif +#define __GLIBC__ 2 +#define __GLIBC_MINOR__ 39 \ No newline at end of file diff --git a/src/__config b/src/__config new file mode 100644 index 00000000..038b8e2c --- /dev/null +++ b/src/__config @@ -0,0 +1,159 @@ +#pragma once +// 42 +#ifndef _LIBCPP_STD_VER +#if __cplusplus <= 201103L +#define _LIBCPP_STD_VER 11 +#elif __cplusplus <= 201402L +#define _LIBCPP_STD_VER 14 +#elif __cplusplus <= 201703L +#define _LIBCPP_STD_VER 17 +#elif __cplusplus <= 202002L +#define _LIBCPP_STD_VER 20 +#else +// Expected release year of the next C++ standard +#define _LIBCPP_STD_VER 23 +#endif +#endif // _LIBCPP_STD_VER + +#if defined(__ELF__) +#define _LIBCPP_OBJECT_FORMAT_ELF 1 +#elif defined(__MACH__) +#define _LIBCPP_OBJECT_FORMAT_MACHO 1 +#elif defined(_WIN32) +#define _LIBCPP_OBJECT_FORMAT_COFF 1 +#elif defined(__wasm__) +#define _LIBCPP_OBJECT_FORMAT_WASM 1 +#elif defined(_AIX) +#define _LIBCPP_OBJECT_FORMAT_XCOFF 1 +#else +// ... add new file formats here ... +#endif +// 71 +// 172 +#ifndef __has_builtin +#define __has_builtin(__x) 0 +#endif +// 176 +// 204 +#if defined(__apple_build_version__) +#define _LIBCPP_COMPILER_CLANG_BASED +#define _LIBCPP_APPLE_CLANG_VER (__apple_build_version__ / 10000) +#elif defined(__clang__) +#define _LIBCPP_COMPILER_CLANG_BASED +#define _LIBCPP_CLANG_VER (__clang_major__ * 100 + __clang_minor__) +#elif defined(__GNUC__) +#define _LIBCPP_COMPILER_GCC +#endif +// 214 +// 490 +#if defined(_LIBCPP_OBJECT_FORMAT_COFF) + +#ifdef _DLL +#define _LIBCPP_CRT_FUNC __declspec(dllimport) +#else +#define _LIBCPP_CRT_FUNC +#endif + +#if defined(_LIBCPP_DISABLE_VISIBILITY_ANNOTATIONS) || (defined(__MINGW32__) && !defined(_LIBCPP_BUILDING_LIBRARY)) +#define _LIBCPP_DLL_VIS +#define _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS +#define _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS +#define _LIBCPP_OVERRIDABLE_FUNC_VIS +#define _LIBCPP_EXPORTED_FROM_ABI +#elif defined(_LIBCPP_BUILDING_LIBRARY) +#define _LIBCPP_DLL_VIS __declspec(dllexport) +#if defined(__MINGW32__) +#define _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS _LIBCPP_DLL_VIS +#define _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS +#else +#define _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS +#define _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS _LIBCPP_DLL_VIS +#endif +#define _LIBCPP_OVERRIDABLE_FUNC_VIS _LIBCPP_DLL_VIS +#define _LIBCPP_EXPORTED_FROM_ABI __declspec(dllexport) +#else +#define _LIBCPP_DLL_VIS __declspec(dllimport) +#define _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS _LIBCPP_DLL_VIS +#define _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS +#define _LIBCPP_OVERRIDABLE_FUNC_VIS +#define _LIBCPP_EXPORTED_FROM_ABI __declspec(dllimport) +#endif + +#define _LIBCPP_TYPE_VIS _LIBCPP_DLL_VIS +#define _LIBCPP_FUNC_VIS _LIBCPP_DLL_VIS +#define _LIBCPP_EXCEPTION_ABI _LIBCPP_DLL_VIS +#define _LIBCPP_HIDDEN +#define _LIBCPP_METHOD_TEMPLATE_IMPLICIT_INSTANTIATION_VIS +#define _LIBCPP_TEMPLATE_VIS +#define _LIBCPP_TEMPLATE_DATA_VIS +#define _LIBCPP_ENUM_VIS + +#else + +#if !defined(_LIBCPP_DISABLE_VISIBILITY_ANNOTATIONS) +#define _LIBCPP_VISIBILITY(vis) __attribute__((__visibility__(vis))) +#else +#define _LIBCPP_VISIBILITY(vis) +#endif + +#define _LIBCPP_HIDDEN _LIBCPP_VISIBILITY("hidden") +#define _LIBCPP_FUNC_VIS _LIBCPP_VISIBILITY("default") +#define _LIBCPP_TYPE_VIS _LIBCPP_VISIBILITY("default") +#define _LIBCPP_TEMPLATE_DATA_VIS _LIBCPP_VISIBILITY("default") +#define _LIBCPP_EXPORTED_FROM_ABI _LIBCPP_VISIBILITY("default") +#define _LIBCPP_EXCEPTION_ABI _LIBCPP_VISIBILITY("default") +#define _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS _LIBCPP_VISIBILITY("default") +#define _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS + +// TODO: Make this a proper customization point or remove the option to override it. +#ifndef _LIBCPP_OVERRIDABLE_FUNC_VIS +#define _LIBCPP_OVERRIDABLE_FUNC_VIS _LIBCPP_VISIBILITY("default") +#endif + +#if !defined(_LIBCPP_DISABLE_VISIBILITY_ANNOTATIONS) +// The inline should be removed once PR32114 is resolved +#define _LIBCPP_METHOD_TEMPLATE_IMPLICIT_INSTANTIATION_VIS inline _LIBCPP_HIDDEN +#else +#define _LIBCPP_METHOD_TEMPLATE_IMPLICIT_INSTANTIATION_VIS +#endif +#ifdef __has_attribute +#define _CSL_HATV __has_attribute(__type_visibility__) +#else +#define _CSL_HATV 0 +#endif +#if !defined(_LIBCPP_DISABLE_VISIBILITY_ANNOTATIONS) +#if _CSL_HATV +#define _LIBCPP_TEMPLATE_VIS __attribute__((__type_visibility__("default"))) +#else +#define _LIBCPP_TEMPLATE_VIS __attribute__((__visibility__("default"))) +#endif +#else +#define _LIBCPP_TEMPLATE_VIS +#endif + +#if !defined(_LIBCPP_DISABLE_VISIBILITY_ANNOTATIONS) && CTL_HATV +#define _LIBCPP_ENUM_VIS __attribute__((__type_visibility__("default"))) +#else +#define _LIBCPP_ENUM_VIS +#endif + +#endif // defined(_LIBCPP_OBJECT_FORMAT_COFF) + // 579 + // 632 + // Inline namespaces are available in Clang/GCC/MSVC regardless of C++ dialect. + // clang-format off +# define _LIBCPP_BEGIN_NAMESPACE_STD namespace std { inline namespace _LIBCPP_ABI_NAMESPACE { +# define _LIBCPP_END_NAMESPACE_STD }} +# define _VSTD std +//638 +//1275 +#ifdef __has_attribute +# if __has_attribute(__nodebug__) +# define _LIBCPP_NODEBUG __attribute__((__nodebug__)) +# else +# define _LIBCPP_NODEBUG +# endif +#else +# define _LIBCPP_NODEBUG +# endif +//1281 \ No newline at end of file diff --git a/src/__type_traits/detail/yes_no_type.hpp b/src/__type_traits/detail/yes_no_type.hpp new file mode 100644 index 00000000..fd0fe2de --- /dev/null +++ b/src/__type_traits/detail/yes_no_type.hpp @@ -0,0 +1,11 @@ +#pragma once +namespace type_traits +{ + + typedef char yes_type; + struct no_type + { + char padding[8]; + }; + +} // namespace type_traits \ No newline at end of file diff --git a/src/__type_traits/is_assignable.hpp b/src/__type_traits/is_assignable.hpp new file mode 100644 index 00000000..21aafbf5 --- /dev/null +++ b/src/__type_traits/is_assignable.hpp @@ -0,0 +1,54 @@ +#pragma once +#include "detail/yes_no_type.hpp" +namespace detail +{ + + struct is_assignable_imp + { + template () = declval())> + static type_traits::yes_type test(int); + + template + static type_traits::no_type test(...); + }; + +} + +template +struct is_assignable : public integral_constant(0)) == sizeof(type_traits::yes_type)> +{ + BOOST_STATIC_ASSERT_MSG(is_complete::value, "Arguments to is_assignable must be complete types"); +}; +template +struct is_assignable : public is_assignable +{ +}; +template +struct is_assignable : public is_assignable +{ +}; +template +struct is_assignable : public is_assignable +{ +}; +template +struct is_assignable : public is_assignable +{ +}; +template +struct is_assignable : public integral_constant +{ +}; +template +struct is_assignable : public integral_constant +{ +}; +template +struct is_assignable : public integral_constant +{ +}; +template +struct is_assignable : public integral_constant +{ +}; +#define __is_assignable(...) is_assignable<__VA_ARGS__>::value \ No newline at end of file diff --git a/src/__type_traits/is_complete.hpp b/src/__type_traits/is_complete.hpp new file mode 100644 index 00000000..62058e67 --- /dev/null +++ b/src/__type_traits/is_complete.hpp @@ -0,0 +1,70 @@ +#pragma once +#include "../detail/workaround.hpp" +// +// We will undef this if the trait isn't fully functional: +// +#define BOOST_TT_HAS_WORKING_IS_COMPLETE + +#if !defined(BOOST_NO_SFINAE_EXPR) && !BOOST_WORKAROUND(BOOST_MSVC, <= 1900) && !BOOST_WORKAROUND(BOOST_GCC_VERSION, < 40600) + +namespace detail +{ + + template + struct ok_tag + { + double d; + char c[N]; + }; + + template + ok_tag check_is_complete(int); + template + char check_is_complete(...); +} + +template +struct is_complete + : public integral_constant::type>::value || (sizeof(detail::check_is_complete(0)) != sizeof(char))> +{ +}; + +#elif !defined(BOOST_NO_SFINAE) && !defined(BOOST_NO_CXX11_FUNCTION_TEMPLATE_DEFAULT_ARGS) && !BOOST_WORKAROUND(BOOST_GCC_VERSION, < 40500) + +namespace detail +{ + + template + struct is_complete_imp + { + template ()))> + static type_traits::yes_type check(U *); + + template + static type_traits::no_type check(...); + + static const bool value = sizeof(check(0)) == sizeof(type_traits::yes_type); + }; + +} // namespace detail + +template +struct is_complete : integral_constant::type>::value || detail::is_complete_imp::value> +{ +}; +template +struct is_complete : is_complete +{ +}; + +#else + +template +struct is_complete + : public integral_constant +{ +}; + +#undef BOOST_TT_HAS_WORKING_IS_COMPLETE + +#endif \ No newline at end of file diff --git a/src/__type_traits/is_constructible.hpp b/src/__type_traits/is_constructible.hpp new file mode 100644 index 00000000..193d966f --- /dev/null +++ b/src/__type_traits/is_constructible.hpp @@ -0,0 +1,66 @@ +#pragma once +#include "is_destructible.hpp" +#include "is_default_constructible.hpp" +namespace detail +{ + + struct is_constructible_imp + { + template ()...))> + static type_traits::yes_type test(int); + template + static type_traits::no_type test(...); + + template ()))> + static type_traits::yes_type test1(int); + template + static type_traits::no_type test1(...); + + template + static type_traits::yes_type ref_test(T); + template + static type_traits::no_type ref_test(...); + }; + +} + +template +struct is_constructible : public integral_constant(0)) == sizeof(type_traits::yes_type)> +{ + BOOST_STATIC_ASSERT_MSG(is_complete::value, "The target type must be complete in order to test for constructibility"); +}; +template +struct is_constructible : public integral_constant::value && sizeof(detail::is_constructible_imp::test1(0)) == sizeof(type_traits::yes_type)> +{ + BOOST_STATIC_ASSERT_MSG(is_complete::value, "The target type must be complete in order to test for constructibility"); +}; +template +struct is_constructible : public integral_constant(declval())) == sizeof(type_traits::yes_type)> +{ +}; +template +struct is_constructible : public integral_constant(declval())) == sizeof(type_traits::yes_type)> +{ +}; + +template <> +struct is_constructible : public false_type +{ +}; +template <> +struct is_constructible : public false_type +{ +}; +template <> +struct is_constructible : public false_type +{ +}; +template <> +struct is_constructible : public false_type +{ +}; + +template +struct is_constructible : public is_default_constructible +{ +}; \ No newline at end of file diff --git a/src/__type_traits/is_convertible.h b/src/__type_traits/is_convertible.h new file mode 100644 index 00000000..345c599d --- /dev/null +++ b/src/__type_traits/is_convertible.h @@ -0,0 +1,126 @@ +#pragma once +#include "../__config" +#include "remove_reference.h" +#if __has_builtin(__is_convertible_to) && !defined(_LIBCPP_USE_IS_CONVERTIBLE_FALLBACK) + + template + struct is_convertible + : public integral_constant + { + }; + +#else // __has_builtin(__is_convertible_to) && !defined(_LIBCPP_USE_IS_CONVERTIBLE_FALLBACK) + + namespace __is_convertible_imp + { + template + void __test_convert(_Tp); + + template + struct __is_convertible_test : public false_type + { + }; + + template + struct __is_convertible_test<_From, _To, + decltype(__is_convertible_imp::__test_convert<_To>(declval<_From>()))> : public true_type + { + }; + + template ::value, + bool _IsFunction = is_function<_Tp>::value, + bool _IsVoid = is_void<_Tp>::value> + struct __is_array_function_or_void + { + enum + { + value = 0 + }; + }; + template + struct __is_array_function_or_void<_Tp, true, false, false> + { + enum + { + value = 1 + }; + }; + template + struct __is_array_function_or_void<_Tp, false, true, false> + { + enum + { + value = 2 + }; + }; + template + struct __is_array_function_or_void<_Tp, false, false, true> + { + enum + { + value = 3 + }; + }; + } + + template >::value> + struct __is_convertible_check + { + static const size_t __v = 0; + }; + + template + struct __is_convertible_check<_Tp, 0> + { + static const size_t __v = sizeof(_Tp); + }; + + template ::value, + unsigned _T2_is_array_function_or_void = __is_convertible_imp::__is_array_function_or_void<_T2>::value> + struct __is_convertible + : public integral_constant::value>{}; + + template + struct __is_convertible<_T1, _T2, 0, 1> : public false_type{}; + template + struct __is_convertible<_T1, _T2, 1, 1> : public false_type{}; + template + struct __is_convertible<_T1, _T2, 2, 1> : public false_type{}; + template + struct __is_convertible<_T1, _T2, 3, 1> : public false_type{}; + + template + struct __is_convertible<_T1, _T2, 0, 2> : public false_type{}; + template + struct __is_convertible<_T1, _T2, 1, 2> : public false_type{}; + template + struct __is_convertible<_T1, _T2, 2, 2> : public false_type{}; + template + struct __is_convertible<_T1, _T2, 3, 2> : public false_type{}; + + template + struct __is_convertible<_T1, _T2, 0, 3> : public false_type{}; + template + struct __is_convertible<_T1, _T2, 1, 3> : public false_type{}; + template + struct __is_convertible<_T1, _T2, 2, 3> : public false_type{}; + template + struct __is_convertible<_T1, _T2, 3, 3> : public true_type{}; + + template + struct is_convertible + : public __is_convertible<_T1, _T2> + { + static const size_t __complete_check1 = __is_convertible_check<_T1>::__v; + static const size_t __complete_check2 = __is_convertible_check<_T2>::__v; + }; + +#endif // __has_builtin(__is_convertible_to) && !defined(_LIBCPP_USE_IS_CONVERTIBLE_FALLBACK) + +#if _LIBCPP_STD_VER > 14 + template + inline constexpr bool is_convertible_v = is_convertible<_From, _To>::value; +#endif \ No newline at end of file diff --git a/src/__type_traits/is_default_constructible.hpp b/src/__type_traits/is_default_constructible.hpp new file mode 100644 index 00000000..5268b8d6 --- /dev/null +++ b/src/__type_traits/is_default_constructible.hpp @@ -0,0 +1,83 @@ +#pragma once +#include "detail/yes_no_type.hpp" +#include "is_complete.hpp" +#include "../static_assert.hpp" +namespace detail +{ + + struct is_default_constructible_imp + { + template + static type_traits::yes_type test(int); + + template + static type_traits::no_type test(...); + }; +#if BOOST_WORKAROUND(BOOST_GCC_VERSION, < 40700) + template + struct is_default_constructible_abstract_filter + { + static const bool value = sizeof(is_default_constructible_imp::test(0)) == sizeof(type_traits::yes_type); + }; + template + struct is_default_constructible_abstract_filter + { + static const bool value = false; + }; +#endif +} + +#if BOOST_WORKAROUND(BOOST_GCC_VERSION, < 40700) +template +struct is_default_constructible : public integral_constant::value>::value> +{ + BOOST_STATIC_ASSERT_MSG(is_complete::value, "Arguments to is_default_constructible must be complete types"); +}; +#else +template +struct is_default_constructible : public integral_constant(0)) == sizeof(type_traits::yes_type)> +{ + BOOST_STATIC_ASSERT_MSG(is_complete::value, "Arguments to is_default_constructible must be complete types"); +}; +#endif +template +struct is_default_constructible : public is_default_constructible +{ +}; +template +struct is_default_constructible : public is_default_constructible +{ +}; +template +struct is_default_constructible : public integral_constant +{ +}; +#if defined(__clang__) || (defined(__GNUC__) && (__GNUC__ <= 5)) || (defined(BOOST_MSVC) && (BOOST_MSVC == 1800)) +template struct _UCXXEXPORT pair; +template +struct is_default_constructible> : public integral_constant::value && is_default_constructible::value> +{ +}; +#endif +#if !defined(BOOST_NO_CXX11_RVALUE_REFERENCES) +template +struct is_default_constructible : public integral_constant +{ +}; +#endif +template <> +struct is_default_constructible : public integral_constant +{ +}; +template <> +struct is_default_constructible : public integral_constant +{ +}; +template <> +struct is_default_constructible : public integral_constant +{ +}; +template <> +struct is_default_constructible : public integral_constant +{ +}; \ No newline at end of file diff --git a/src/__type_traits/is_destructible.hpp b/src/__type_traits/is_destructible.hpp new file mode 100644 index 00000000..c3da1635 --- /dev/null +++ b/src/__type_traits/is_destructible.hpp @@ -0,0 +1,71 @@ +#pragma once +#include "detail/yes_no_type.hpp" +#include "is_complete.hpp" +#include "../static_assert.hpp" +#if !defined(BOOST_NO_CXX11_DECLTYPE) && !BOOST_WORKAROUND(BOOST_MSVC, < 1800) +namespace detail +{ + + struct is_destructible_imp + { + template ().~T())> + static type_traits::yes_type test(int); + template + static type_traits::no_type test(...); + }; + +} + +template +struct is_destructible : public integral_constant(0)) == sizeof(type_traits::yes_type)> +{ + BOOST_STATIC_ASSERT_MSG(is_complete::value, "Arguments to is_destructible must be complete types"); +}; + +#else + +#include +#include + +// We don't know how to implement this: +template +struct is_destructible : public integral_constant::value || is_class::value> +{ + BOOST_STATIC_ASSERT_MSG(is_complete::value, "Arguments to is_destructible must be complete types"); +}; +#endif + +template <> +struct is_destructible : public false_type +{ +}; +template <> +struct is_destructible : public false_type +{ +}; +template <> +struct is_destructible : public false_type +{ +}; +template <> +struct is_destructible : public false_type +{ +}; +template +struct is_destructible : public is_destructible +{ +}; +#ifndef BOOST_NO_CXX11_RVALUE_REFERENCES +template +struct is_destructible : public is_destructible +{ +}; +#endif +template +struct is_destructible : public is_destructible +{ +}; +template +struct is_destructible : public is_destructible +{ +}; \ No newline at end of file diff --git a/src/__type_traits/is_nothrow_constructible.h b/src/__type_traits/is_nothrow_constructible.h new file mode 100644 index 00000000..ba96f347 --- /dev/null +++ b/src/__type_traits/is_nothrow_constructible.h @@ -0,0 +1,54 @@ +#pragma once +#include "../__config" +#if __has_builtin(__is_nothrow_constructible) + + template < + class _Tp, class... _Args> + struct _LIBCPP_TEMPLATE_VIS is_nothrow_constructible + : public integral_constant + { + }; +#else + + template + struct __libcpp_is_nothrow_constructible; + + template + struct __libcpp_is_nothrow_constructible + : public integral_constant()...))> + { + }; + + template + void __implicit_conversion_to(_Tp) noexcept {} + + template + struct __libcpp_is_nothrow_constructible + : public integral_constant(declval<_Arg>()))> + { + }; + + template + struct __libcpp_is_nothrow_constructible + : public false_type + { + }; + + template + struct _LIBCPP_TEMPLATE_VIS is_nothrow_constructible + : __libcpp_is_nothrow_constructible::value, is_reference<_Tp>::value, _Tp, _Args...> + { + }; + + template + struct _LIBCPP_TEMPLATE_VIS is_nothrow_constructible<_Tp[_Ns]> + : __libcpp_is_nothrow_constructible::value, is_reference<_Tp>::value, _Tp> + { + }; +#define __is_nothrow_constructible(...) is_nothrow_constructible<__VA_ARGS__>::value +#endif // __has_builtin(__is_nothrow_constructible) + +#if _LIBCPP_STD_VER > 14 + template + inline constexpr bool is_nothrow_constructible_v = is_nothrow_constructible<_Tp, _Args...>::value; +#endif \ No newline at end of file diff --git a/src/__type_traits/is_nothrow_move_assignable.hpp b/src/__type_traits/is_nothrow_move_assignable.hpp new file mode 100644 index 00000000..313772b8 --- /dev/null +++ b/src/__type_traits/is_nothrow_move_assignable.hpp @@ -0,0 +1,111 @@ +#pragma once +#include "../static_assert.hpp" +#include "is_complete.hpp" +#include "../config/detail/suffix.hpp" +#ifdef BOOST_IS_NOTHROW_MOVE_ASSIGN + +template +struct is_nothrow_move_assignable : public integral_constant +{ + BOOST_STATIC_ASSERT_MSG(is_complete::value, "Arguments to is_nothrow_move_assignable must be complete types"); +}; +template +struct is_nothrow_move_assignable : public false_type +{ +}; +template +struct is_nothrow_move_assignable : public false_type +{ +}; +template +struct is_nothrow_move_assignable : public false_type +{ +}; +template +struct is_nothrow_move_assignable : public false_type +{ +}; +#if !defined(BOOST_NO_CXX11_RVALUE_REFERENCES) +template +struct is_nothrow_move_assignable : public false_type +{ +}; +#endif + +#elif !defined(BOOST_NO_CXX11_NOEXCEPT) && !defined(BOOST_NO_SFINAE_EXPR) && !BOOST_WORKAROUND(BOOST_GCC_VERSION, < 40700) + +namespace detail +{ + + template + struct false_or_cpp11_noexcept_move_assignable : public std::false_type + { + }; + + template + struct false_or_cpp11_noexcept_move_assignable< + T, + typename std::enable_if() = std::declval())>::type> : public std::integral_constant() = std::declval())> + { + }; + +} + +template +struct is_nothrow_move_assignable : public integral_constant::value> +{ + BOOST_STATIC_ASSERT_MSG(is_complete::value, "Arguments to is_nothrow_move_assignable must be complete types"); +}; + +template +struct is_nothrow_move_assignable : public false_type +{ +}; +template +struct is_nothrow_move_assignable : public false_type +{ +}; +template +struct is_nothrow_move_assignable : public false_type +{ +}; +template +struct is_nothrow_move_assignable : public false_type +{ +}; +#ifndef BOOST_NO_CXX11_RVALUE_REFERENCES +template +struct is_nothrow_move_assignable : public false_type +{ +}; +#endif + +#else + +template +struct is_nothrow_move_assignable : public integral_constant::value || has_nothrow_assign::value) && !is_array::value> +{ + BOOST_STATIC_ASSERT_MSG(is_complete::value, "Arguments to is_nothrow_move_assignable must be complete types"); +}; + +#endif + +template <> +struct is_nothrow_move_assignable : public false_type +{ +}; +#ifndef BOOST_NO_CV_VOID_SPECIALIZATIONS +template <> +struct is_nothrow_move_assignable : public false_type +{ +}; +template <> +struct is_nothrow_move_assignable : public false_type +{ +}; +template <> +struct is_nothrow_move_assignable : public false_type +{ +}; +#endif \ No newline at end of file diff --git a/src/__type_traits/remove_reference.h b/src/__type_traits/remove_reference.h new file mode 100644 index 00000000..04bfa1d3 --- /dev/null +++ b/src/__type_traits/remove_reference.h @@ -0,0 +1,6 @@ +#pragma once +#if __has_builtin(__remove_reference_t) +#else + template + using __libcpp_remove_reference_t = typename remove_reference<_Tp>::type; +#endif // __has_builtin(__remove_reference_t) \ No newline at end of file diff --git a/src/__utility/integer_sequence.h b/src/__utility/integer_sequence.h new file mode 100644 index 00000000..39a6c158 --- /dev/null +++ b/src/__utility/integer_sequence.h @@ -0,0 +1,184 @@ +#pragma once +#include "../__config" +template +struct __tuple_indices; + +template +struct __integer_sequence +{ + template