1 В избранное 0 Ответвления 0

OSCHINA-MIRROR/Neur1n-n.h

Присоединиться к Gitlife
Откройте для себя и примите участие в публичных проектах с открытым исходным кодом с участием более 10 миллионов разработчиков. Приватные репозитории также полностью бесплатны :)
Присоединиться бесплатно
Клонировать/Скачать
README.md 23 КБ
Копировать Редактировать Web IDE Исходные данные Просмотреть построчно История
gitlife-traslator Отправлено 30.11.2024 07:13 cae6f55

Начало работы

  • Установка* Поместите x.h в свой проект.

  • Использование* x.h — это библиотека с одним заголовком, что означает, что пользователи могут просто использовать её функциональные возможности, включив её где угодно:

// в каком-то файле foo.h
#include "x.h"

// в каком-то файле foo.c
#include "x.h"

Документация

  • Переключение функций* Предоставляется несколько макросов для переключения функций, некоторые из которых можно использовать, чтобы избежать избыточных зависимостей сборки в некоторых случаях.
#ifndef X_ENABLE_ATOMIC
#define X_ENABLE_ATOMIC (0)
#endif

#ifndef X_ENABLE_CONCURRENCY
#define X_ENABLE_CONCURRENCY (0)
#endif

#ifndef X_ENABLE_CUDA
#define X_ENABLE_CUDA (0)
#endif

#ifndef X_ENABLE_SOCKET
#define X_ENABLE_SOCKET (0)
#endif

#ifndef X_ENABLE_STRUCT_FUNCTION
#define X_ENABLE_STRUCT_FUNCTION (1)
#endif

  • Генератор номеров версий* X_VER: объединяет числа major, minor и patch в номер версии. Диапазоны каждого компонента:
  • major: [0, 99]
  • minor: [0, 99]
  • patch: [0, 99999].

Большой диапазон патчей позволяет номеру версии работать с _MSC_FULL_VER.


  • Обнаружение архитектуры*
  • X_32BIT: определяется как 1, если архитектура 32-битная, иначе 0.

  • X_64BIT: определяется как 1, если архитектура 64-битная, иначе 0.

  • X_ARM: определяется как 1, если архитектура ARM, иначе 0. Иначе.

  • X_ARM64: определяется как 1, если архитектура 64-битная ARM, иначе 0.

  • X_X86: определяется как 1, если архитектура 32-битная x86, иначе 0.

  • X_X64: определяется как 1, если архитектура 64-битная x86, иначе 0.


Определение компилятора

  • X_CLANG: определяется номером версии Clang, если он используется, иначе 0.
  • X_GCC: определяется номером версии GCC, если он используется, иначе 0.
  • X_MSVC: определяется номером версии MSVC, если он используется, иначе 0.

Номер версии генерируется с помощью X_VER. Например, X_VER(15, 0, 6) (версия 15.0.6) приводит к результату 150000006.


Обнаружение ОС

  • X_CYGWIN: определяется номером версии Cygwin, если это целевая ОС, иначе 0.
  • X_LINUX: определяется как 1, если Linux — целевая ОС, иначе 0.
  • X_MACOS: определяется номером, если MACOS — целевая ОС, иначе 0.
  • X_WINDOWS: определяется как 1, если Windows — целевая ОС, иначе 0.

Обнаружение платформы

  • X_ANDROID: определяется как 1, если Android — целевая платформа, иначе 0.
  • X_MINGW: определяется как 1, если MinGW32/64 — целевая платформа, иначе 0.
  • X_MINGW32: определяется номером, если MinGW32 — целевая платформа, иначе 0.
  • X_MINGW64: определяется номером, если MinGW64 — целевая платформа, иначе 0.

X_EXPORT, X_IMPORT

#ifndef X_EXPORT
#if X_WINDOWS
#define X_EXPORT __declspec(dllexport)
#else
#define X_EXPORT __attribute__ ((visibility("default")))
#endif
#endif

#ifndef X_IMPORT
#if X_WINDOWS
#define X_IMPORT __declspec(dllimport)
#else
#define X_IMPORT __attribute__ ((visibility("hidden")))
#endif
#endif

См. Microsoft Docs и GCC Wiki для получения дополнительной информации.


X_KEY

#define X_KEY_ESC   (0x1B)
#define X_KEY_A     (0x41)
#define X_KEY_B     (0x42)
#define X_KEY_C     (0x43)
#define X_KEY_D     (0x44)
#define X_KEY_Q     (0x51)
#if X_WINDOWS
#define X_KEY_LEFT  (0x4B)
#define X_KEY_UP    (0x48)
#define X_KEY_RIGHT (0x4D)
#define X_KEY_DOWN  (0x50)
#else
#define X_KEY_LEFT  (-1)
#define X_KEY_UP    (-2)
#define X_KEY_RIGHT (-3)
#define X_KEY_DOWN  (-4)
#endif

Несколько макросов виртуальных клавиш, большинство из которых определяются соответствующим ASCII-кодом. Однако стрелки обрабатываются по-разному в разных ОС (пожалуйста, сообщите мне, если это утверждение неверно), они определены как отрицательные целые числа для обхода. Пожалуйста, проверьте x_getch для их использования.


x_assert Макрос, который включает функцию утверждения для сборок отладки и выпуска. Для сборки отладки это то же самое, что и макрос утверждения в заголовке assert.h/cassert.

x_assert(expr)

Параметры

  • expr: выражение утверждения.

Примеры

x_assert(1 == 1);
x_assert(1 != 1);

x_bit Макрос, используемый для генерации целого числа, в котором только n-й бит установлен в 1. Это полезно, когда нужно перечисления вроде 0b0001, 0b0010, 0b0100 для выполнения операций &, |, ~.

T x_bit(bit)  // В этом документе T обозначает тип возвращаемого значения из макроса.

Параметры

  • bit: спецификация, для какого бита целого числа должен быть установлен 1.

Возвращает

  • Сгенерированное целое число, может быть int, long и т. д.

Пример

enum
{
  FLAG_NONE   = 0,
  FLAG_READ   = x_bit(1),
  FLAG_WRITE  = x_bit(2),
};

int read_and_write = FLAG_READ | FLAG_WRITE;

x_buffer_valid Определение этого макроса должно было хорошо объяснить себя:

#define x_buffer_valid(buffer, size) \
  (((buffer) == NULL && (size) == 0) || ((buffer) != NULL && (size) != 0))

Он не реализован как функция, поскольку size может быть int, size_t и т.д. Поэтому передавайте аргументы осторожно.

Параметры

  • buffer: указатель на буфер.
  • size: размер содержимого в указателе.

Возвращает

  • true, если буфер действителен.

Пример

int read_file(const char* file, void* buffer, size_t size)
{
  if (!x_buffer_valid(buffer,
``` **size)) {**

    вернуть EINVAL;
  }

  // operations

  вернуть 0;
}

x_count

Получить длину массива. Этот макрос работает только со статическими массивами.

T x_count(array)

Для C++ это реализовано как шаблонная функция:

template<class T, size_t N>
size_t x_count(const T (&array)[N])
{
  return N;
}

Параметры

  • array: массив, размер которого нужно запросить.

Возвращает

  • Длину (количество элементов) входного массива.

Примеры

int a[5] = {1, 2, 3, 4, 5};

for (size_t i = 0; i < x_count(a); ++i)
{
  printf("%d", a[i]);
}

x_fail

Макрос для проверки, указывает ли номер ошибки на сбой. Работает только с системой обработки ошибок, которая определяет 0 как успех, например, POSIX errno.

bool x_fail(err)

Параметры

  • err: номер ошибки.

Возвращает

Логическое значение, указывающее, означает ли номер ошибки сбой.

Примеры

int err = EINVAL;
if (x_fail(err))
{
  printf("%s\n", strerror(err));
}

x_free

Макрос для освобождения блока памяти, выделенного в куче, и установки его в NULL.

void x_free(ptr)

Параметры

  • ptr: указатель, которому ранее была выделена память.

Примеры

int *a = (int*)malloc(5 * sizeof(int));
x_free(a);

x_Pi

Макрос для получения константы Пи. Входной аргумент используется для указания целевого типа данных.

T x_Pi(T)

В C++ можно использовать следующий шаблон:

template<class T>
static constexpr T x_Pi = (T)3.141592653589793238462643383279502884197169399375;
// Использование: x_Pi<float>, x_Pi<double>, и т. д.

Параметры

  • T: целевой тип, например float, double, long.

Возвращает

  • Пи указанного типа.

Примеры

float a = x_pi(float);
double b = x_pi(double);

x_succ

Макрос для проверки, указывает ли номер ошибки на успех. Работает только с системой обработки ошибок, которая определяет 0 как успех, например, POSIX errno.

bool x_succ(err)

Параметры

  • err: номер ошибки.

Возвращает

Логическое значение, указывающее, означает ли номер ошибки успех.

Примеры

int err = 0;
if (x_succ(err))
{
  printf("%s\n", strerror(err));
}

x_cpu_count

size_t x_cpu_count()

Возвращает

Количество процессоров текущего хоста.


x_duration

double x_duration(const struct timespec start, const struct timespec end, const char* unit)

Параметры

  • start: начальная точка времени.
  • end: конечная точка времени.
  • unit: единица результата.

Возвращает

Длительность двух временных точек в указанной единице.


x_file_size

long long x_file_size(const char* file)

Параметры

  • file: имя файла, размер которого необходимо проверить.

Возвращает

Размер файла в байтах.


x_full_path

const char* x_full_path(char* dst, const char* src)

Параметры

  • dst: полный/абсолютный путь к входному файлу. Перед передачей этой функции он должен быть размещён в памяти, иначе будет возвращено NULL.
  • src: (возможно, относительный) путь к файлу.

Возвращает

То же значение, содержащееся в dst, или NULL, если операция не удалась.

Примеры

const char* file = "./foo/bar.txt";
char buf[X_PATH_MAX] = {0};
x_full_path(buf, file);

x_getch

Кроссплатформенная версия функции Win32 _getch.

int x_getch()

Возвращает

Нажатую клавишу.

Примеры

Эта функция работает только с консольными программами. Её можно использовать для прерывания бесконечного цикла вручную:

int main(int argc, char** argv)
{
  while (true)
  {
    if (x_getch() == X_KEY_ESC)
    {
      break;  // При нажатии клавиши «Esc» цикл прерывается.
    }

    x_sleep(10);
  }

  return 0;
}

x_now

struct timespec x_now();

Возвращает

Экземпляр struct timespec, указывающий текущее время.


x_path_exists

bool x_path_exist(const char* path)

Параметры

  • path: путь к файлу или каталогу. for // определение метода запроса сообщения об ошибке и самого метода. Пожалуйста, // проверьте test/test_x_err.c, который должен быть самоочевидным. // // В противном случае описание будет получено в соответствии со значением // ошибки через FormatMessage из Win32 API или strerror из POSIX. const char* x_err_msg(char* msg, const size_t msz, const x_err err, ... /* const int method, const char* generator*/);

// Создаёт экземпляр x_err. x_err x_err_set(const int32_t cat, const int32_val);

// Может использоваться для инициализации экземпляра x_err. x_err x_ok();


#### Примеры
Пожалуйста, проверьте *test/test_x_err.c* и *test/test_x_err.cu*.

---

### Параллелизм
Эти функции во многом похожи на те, что предоставляются библиотекой поддержки параллелизма C11
- x\_cnd: утилиты условных переменных.
- x\_mtx: утилиты мьютекса.
- x\_sem: семафорные утилиты.
- x\_thd: утилиты потоков.
- x\_atomic\_B: атомарные утилиты 8-битных, 16-битных, 32-битных, 64-битных данных, bool, указателей (`void*`), флагов. Структуры и функции генерируются макросами во время компиляции.

Доступные типы атомарных данных:
- x\_atomic\_8: содержит данные `uint8_t`.
- x\_atomic\_16: содержит данные `uint16_t`.
- x\_atomic\_32: содержит данные `uint32_t`.
- x\_atomic\_64: содержит данные `uint64_t`.
- x\_atomic\_ptr: содержит данные типа `uint32_t` или `uint64_t` (`sizeof(void*)`, зависит от архитектуры).
- x\_atomic\_bool: содержит данные `_Bool`.
- x\_atomic_flag: содержит данные `_Bool`.

Доступные атомарные функции (где `B` — один из `8`, `16`, `32`, `64`, `ptr`,
`bool`, а `T` — один из `uint8_t`, `uint16_t`, `uint32_t`, `uint64_t`, `void*`,
'bool'):

```c
void x_atomic_init_B(volatile x_atomic_B* obj, T desired)

void x_atomic_store_B(volatile x_atomic_B* obj, T desired, x_memory_order order)

T x_atomic_load_B(volatile x_atomic_B* obj, x_memory_order order)

T x_atomic_exchange_B(volatile x_atomic_B* obj, T desired, x_memory_order order)

bool x_atomic_compare_exchange_B(
    volatile x_atomic_B* obj, T* expected, T desired,
    x_memory_order succ, x_memory_order fail)

T x_atomic_fetch_add_B(volatile x_atomic_B* obj, T desired, x_memory_order order)

T x_atomic_fetch_sub_B(volatile x_atomic_B* obj, T desired, x_memory_order order)

T x_atomic_fetch_Or_B(volatile x_atomic_B* obj, T desired, x_memory_order order)

T x_atomic_fetch_Xor_B(volatile x_atomic_B* obj, T desired, x_memory_order order)

T x_atomic_fetch_And_B(volatile x_atomic_B* obj, T desired, x_memory_order order)

#define x_kill_dependency(x) (x)

#define x_atomic_is_lock_free(T) _x_is_size_lock_free(sizeof(T))

bool x_atomic_flag_test_and_set(volatile x_atomic_flag* obj, x_memory_order order)

void x_atomic_flag_clear(volatile x_atomic_flag* obj, x_memory_order order)

void x_atomic_signal_fence(const x_memory_order order)

void x_atomic_thread_fence(const x_memory_order order)

Функциональные указатели внутри x_atomic_B предоставляются унифицированным API, чтобы различные атомарные объекты можно было легко заменить во время рефакторинга кода. Например:

// before
x_atomic_32 obj = X_ATOMIC_VAR_INIT(32);  // был 32-битный тип данных
obj.init(&obj, 0);
obj.fetch_add(&obj, 1);

// after
x_atomic_64 obj = X_ATOMIC_VAR_INIT(64);  // рефакторинг до 64-битного
obj.init(&obj, 0);                        // нет необходимости это менять
obj.fetch_add(&obj, 1);                   // это тоже, ура!

Определение x_memory_order:

typedef enum _x_memory_order_
{
#if X_CLANG || X_GCC
    x_mo_relaxed = __ATOMIC_RELAXED,
    x_mo_consume = __ATOMIC_CONSUME,
    x_mo_acquire = __ATOMIC_ACQUIRE,
    x_mo_release = __ATOMIC_RELEASE,
    x_mo_acq_rel = __ATOMIC_ACQ_REL,
    x_mo_seq_cst = __ATOMIC_SEQ_CST
#else
    x_mo_relaxed = 0,
    x_mo_consume = 1,
    x_mo_acquire = 2,
    x_mo_release = 3,
    x_mo_acq_rel = 4,
    x_mo_seq_cst = 5
#endif
} x_memory_order;

За исключением x_atomic_bool и x_atomic_flag, объекты x_atomic_B заботятся только о том, сколько битов имеет внутренний тип данных. Поэтому при сохранении или загрузке данных в эти атомарные объекты следует выполнять правильное приведение типов. CRC-32 (on the fly) Checksum

uint32_t x_cks_crc32(const void* data, const size_t size, const uint32_t* prev)

Параметры:

  • data: Исходные данные контрольной суммы.
  • size: Размер данных в байтах.
  • prev: Необязательный предыдущий результат контрольной суммы. Может быть NULL.

Возвращает:

  • Контрольную сумму CRC-32.

Контрольная сумма заголовка IPv4

uint16_t x_cks_rfc1071(const void* data, const size_t size)

Параметры:

  • data: Исходные данные контрольной суммы.
  • size: Размер данных в байтах.

Возвращает:

  • Контрольная сумма заголовка IPv4. Подробнее см. в RFC 1071.

Контрольная сумма XOR

uint8_t x_cks_xor(const void* data, const size_t size)

Параметры:

  • data: Исходные данные контрольной суммы.
  • size: Размер данных в байтах.

Возвращает:

  • контрольную сумму, рассчитанную путём выполнения XOR всех данных в data.

x_pkt

Утилиты для работы с пакетами. Исходный код должен был объяснить сам себя.


x_iov

Утилиты вектора ввода-вывода. Исходный код должен был объяснить сам себя.


x_skt

Утилиты сокетов.


x_node

Узлы для связанных очередей и списков.


x_deque

Простая двусторонняя очередь без синхронизации.


x_lfque

Очередь без блокировки.


x_tlque

Двухблокировочная очередь.


x_tictoc

Утилиты для записи времени выполнения кода.

typedef struct _x_tictoc_
{
  struct timespec start;  // Временная метка начала записи.
  double elapsed;         // Время выполнения последнего цикла.

  struct
  {
    bool ready;  // Устанавливается в значение `true`, как только достигаются целевые циклы выполнения.
    size_t cyc;  // Общее количество циклов, которые должны быть записаны.
    double sum;  // Общее затраченное время.
    double avg;  // Среднее время выполнения на цикл.
    struct
    {
      size_t idx;  // Индекс цикла, в котором произошло максимальное/минимальное время выполнения.
      double val;  // Время выполнения `idx`-го цикла.
    } max, min;  // Информация о максимальном (max) и минимальном (min) времени выполнения.
  } report;
} x_tictoc;

X_INLINE int x_tictoc_init(x_tictoc* tictoc);

// Начало отсчёта времени.
X_INLINE int x_tic(x_tictoc* tictoc, const bool echo);

// Конец отсчёта времени.
X_INLINE int x_toc(x_tictoc* tictoc, const char* unit, const bool echo);

// Конец отсчёта времени в многоцикловой операции записи.
X_INLINE int x_toc_ex(
    x_tictoc* tictoc,
    const char* unit, const long long cycle, const char* title,
    char* echo, size_t* size);

Лицензия

Распространяется под лицензией Mulan PSL v2. Подробнее см. LICENSE.

Опубликовать ( 0 )

Вы можете оставить комментарий после Вход в систему

1
https://api.gitlife.ru/oschina-mirror/Neur1n-n.h.git
git@api.gitlife.ru:oschina-mirror/Neur1n-n.h.git
oschina-mirror
Neur1n-n.h
Neur1n-n.h
v0.7