Clang

Вопросы написания собственного программного кода (на любых языках)

Модератор: Olej

Аватара пользователя
Olej
Писатель
Сообщения: 21338
Зарегистрирован: 24 сен 2011, 14:22
Откуда: Харьков
Контактная информация:

Re: Clang

Непрочитанное сообщение Olej » 08 окт 2013, 23:12

Olej писал(а): Ох, что-то мне подсказывает, что нужно сносить нафиг все репозитарные пакеты RPM (и то же самое в любом дистрибутиве Linux) и ставить всё это из исходников:
- LLVM;
- Clang;
- libc++;
Гораздо лучше дела с Clang, похоже, обстоят в репозитариях Debian 7.0: поставил из репозитария, проверил - все тестовые примеры работают сразу и без артефактов.
Так вот происходило (было проверено) при установке вот этой сборки Debian: Экспериментальная сборка дистрибутива Debian Wheezy + MATE.

Аватара пользователя
Olej
Писатель
Сообщения: 21338
Зарегистрирован: 24 сен 2011, 14:22
Откуда: Харьков
Контактная информация:

Re: Clang

Непрочитанное сообщение Olej » 10 окт 2013, 16:22

Вопросы использования Clang, а главный из таких вопросов остаётся степень совместимости по коду с GCC, будут попутно упоминаться в теме: язык C в Linux: вопросы начального уровня. Но там, как и понятно из названия, только относительно использования Clang для языка C (не C++).

Попутно остаются интересными вопросы сравнения Clang и GCC:
- по размерам создаваемых исполнимых файлов;
- насколько они изменяются в процессе strip (сколько много в файлах отладочной информации)?
- сравнительная эффективность генерируемого кода;
- степень зависимости оптимизации, для того и другого компилятора, от опций -O, -O2, -O3 и т.п.

Аватара пользователя
Olej
Писатель
Сообщения: 21338
Зарегистрирован: 24 сен 2011, 14:22
Откуда: Харьков
Контактная информация:

Re: Clang

Непрочитанное сообщение Olej » 07 янв 2014, 17:33

Olej писал(а):Вопросы использования Clang, а главный из таких вопросов остаётся степень совместимости по коду с GCC, будут попутно упоминаться в теме: язык C в Linux: вопросы начального уровня. Но там, как и понятно из названия, только относительно использования Clang для языка C (не C++).
Ещё раз столкнулся с вопросами совместимости кода для GCC и Clang (относительно языка C).
Это очень важно, т.к. объявлено, что:
Целью проекта Clang является создание замены GNU Compiler Collection (GCC)
В 2013г. было объявлено, что с помощью Clang было полностью собрано ядро Linux из оригинальных исходных кодов - это очень высокая степень совместимости.

Но язык C имеет достаточно много расширений, нескольких разных родов:
- расширения стандартами C89, C99 - комплексные числа и арифметика, языковая локализация и широкие символы wchar_t и т.д.
- расширения, которые вносит только проект GCC GNU: инлайновые ассемблерные вставки, вложенные описания функций и т.д.
Интересна совместимость вот в смысле расширений.
Вот несколько таких тестов:

Код: Выделить всё

//---------------------------------------------------------

static void show( int *arr, int row, int col ) {
   int r, c;
   printf( "матрица : %d x %d [ %d ]\n",
           row, col, row * col );
   for( r = 0; r < row; r++ ) {
      for( c = 0; c < col; c++ )
         printf( "%3d", arr[ r * col + c ] );
      printf( "\n" );
   }
}

static void transpa( int *arr, int *row, int *col ) {
   int r, c;
   int wrk[ *row * *col ];    // массив с динамической размерностью
   for( r = 0; r < *row; r++ )
      for( c = 0; c < *col; c++ ) {
         int i1 = r * *col + c,
             i2 = c * *row + r;
         wrk[ i2 ] = arr[ i1 ];
      }
   for( r = 0; r < *row * *col; r++ ) {
      arr[ r ] = wrk[ r ];
   }
   r = *row;
   *row = *col;
   *col = r;
}

#define COL 5
#define ROW 2

void test02( void ) {           // динамические массивы (C99)
   int c[ ROW ][ COL ] = {
          { 1, 2, 3, 4, 5 },
          { 2, 3, 4, 5, 6 }
       },
       col = COL, row = ROW;
   show( (int*)c, row, col );
   printf( "транспонирование не квадратной матрицы:\n" ); 
   transpa( (int*)c, &row, &col );
   show( (int*)c, row, col );
}

//---------------------------------------------------------

static unsigned long long rdtsc( void ) {
   unsigned long long int x;
   asm volatile ( "rdtsc" : "=A" (x) ); // команда RDTSC
   return x;
}

void test03( void ) {                   // ассемблерные вставки (GCC)
   time_t t1, t2;
   unsigned long long cf, cs; 
   time( &t1 );
   while( t1 == time( &t2 ) ) cf  = rdtsc(); // начало очередной секунды
   while( t2 == time( &t1 ) ) cs  = rdtsc(); // завершение этой секунды
   printf( "тактовая частота процессора %.3f Ghz\n",
           (double)( cs - cf ) / 1.E9 ); 
}

//---------------------------------------------------------

typedef struct vararr {
   int n, data[ 0 ];
} vararr_t;

void varfunc( vararr_t *a ) {
   int ni = a->n, j;
   printf( "массив размера %d\t=> { ", ni );
   int *va = (int*)a;
   for( j = 1; j <= ni; j++ )
      printf( "%d%s", va[ j ], j != ni ? " , " : " }\n" );
}

void test04( void ) {
   printf( "структуры переменного размера:\n" );
   int var[] = { 3, 5, 7, 10 }, i;
   for( i = 0; i < sizeof( var ) / sizeof( *var ); i++ ) {
      int len = var[ i ], j;
      vararr_t *arr = (vararr_t*)calloc( len + 1, sizeof( int ) );
      arr->n = len;
      for( j = 0; j < len; j++ ) arr->data[ j ] = j + 1;
      varfunc( arr );
      free( arr );
   }
}

//---------------------------------------------------------

#define DIV 10.
        
void test05( void ) {    // максимальная точность итерационных вычислений
   printf( "максимальная точность итерационных вычислений:\n" );
   int i;
   float x = 1.;
   double y = 1.;
   long double z = 1.;
   for( i = 0; ; i++ ) {
      if( (float)1. + x == (float)1. + x / (float)DIV ) break;
      x /= (float)DIV;
   }
   printf( "для float\t: %e (число итераций %d)\n", x, i );
   for( i = 0; ; i++ ) {
      if( ( (double)1. + y ) == ( (double)1. + y / (double)DIV ) ) break;
      y /= (double)DIV;
   }
   printf( "для double\t: %e (число итераций %d)\n", y, i );
   for( i = 0; ; i++ ) {
      if( ( (long double)1. + z ) == ( (long double)1. + z / (long double)DIV ) ) break;
      z /= (long double)DIV;
   }
   printf( "для long double\t: %Le (число итераций %d)\n", z, i );
}

//---------------------------------------------------------

Видно, что тесты выполняются успешно:

Код: Выделить всё

olej@notebook:~/2014_WORK/OWN.BOOKS/BOOK.IBM/C/EXMP$ make -fMakefile.clang clang
clang -xc -Wall -lm -O clang.c -o clang
olej@notebook:~/2014_WORK/OWN.BOOKS/BOOK.IBM/C/EXMP$ ./clang 
00 ---------------------------------------
матрица : 2 x 5 [ 10 ]
  1  2  3  4  5
  2  3  4  5  6
транспонирование не квадратной матрицы:
матрица : 5 x 2 [ 10 ]
  1  2
  2  3
  3  4
  4  5
  5  6
01 ---------------------------------------
тактовая частота процессора 1.662 Ghz
02 ---------------------------------------
структуры переменного размера:
массив размера 3	=> { 1 , 2 , 3 }
массив размера 5	=> { 1 , 2 , 3 , 4 , 5 }
массив размера 7	=> { 1 , 2 , 3 , 4 , 5 , 6 , 7 }
массив размера 10	=> { 1 , 2 , 3 , 4 , 5 , 6 , 7 , 8 , 9 , 10 }
03 ---------------------------------------
максимальная точность итерационных вычислений:
для float	: 9.999999e-09 (число итераций 8)
для double	: 1.000000e-16 (число итераций 16)
для long double	: 1.000000e-20 (число итераций 20)
------------------------------------------
Интересный последний тест - максимальная точность итерационных вычислений.
Если его же компилировать GCC получим:

Код: Выделить всё

olej@notebook:~/2014_WORK/OWN.BOOKS/BOOK.IBM/C/EXMP$ ./clang 3
03 --------------------------------------- 
максимальная точность итерационных вычислений: 
для float:       1.000000e-08 (число итераций 8) 
для double:      1.000000e-16 (число итераций 16) 
для long double: 1.000000e-20 (число итераций 20) 
------------------------------------------ 
Обратим внимание на то, что результат Clang (9.999999e-09) совпадает с полученным в GCC (1.000000e-08) по смыслу, но не совпадает по численному представлению. Это должно быть напоминанием, что при переносе кода под Clang не следует ожидать формальной численной идентичности, такое предположение может создать серьёзные трудности в отладке кода. Ещё более выраженным это будет при вовлечении оптимизации (-O2, -O3 и т.д.) генерируемого кода (уровень которой, как утверждается, у Clang потенциально значительно выше, чем у GCC).
Вложения
clang.c
(4.24 КБ) 387 скачиваний

Аватара пользователя
Olej
Писатель
Сообщения: 21338
Зарегистрирован: 24 сен 2011, 14:22
Откуда: Харьков
Контактная информация:

Re: Clang

Непрочитанное сообщение Olej » 07 янв 2014, 17:46

Olej писал(а): Но язык C имеет достаточно много расширений, нескольких разных родов:
- расширения стандартами C89, C99 - комплексные числа и арифметика, языковая локализация и широкие символы wchar_t и т.д.
- расширения, которые вносит только проект GCC GNU: инлайновые ассемблерные вставки, вложенные описания функций и т.д.
Интересна совместимость вот в смысле расширений.
Из всех расширений GCC, я обнаружил только одно расширение, которое не поддерживается Clang: вложенные определения функций ... типа такого:

Код: Выделить всё

void test01( void ) {         // расширение GCC
   int array[] = { 1, -2, 3, -4, 5, -6, 7 },
       size = sizeof( array ) / sizeof( *array ), i;
   void pow2( void ) {        // вложенное описание функции pow2()
      int decr( int arg ) {   // ещё один уровень вложенности функции decr()
         return arg - 1;
      }
      for( i = 0; i < size; i++ )
         array[ i ] = decr( array[ i ] ) * decr( array[ i ] );
   }
   printf( "вложенные функции GCC:\n" );
   printf( "до\t:" );
   for( i = 0; i < size; i++ )
      printf( "%2d%s", array[ i ], ( i == size - 1 ? "\n" : " , " ) );
   pow2();
   printf( "после\t:" );
   for( i = 0; i < size; i++ )
      printf( "%2d%s", array[ i ], ( i == size - 1 ? "\n" : " , " ) );
}
В GCC это нормально проходит:
olej@notebook:~/2014_WORK/OWN.BOOKS/BOOK.IBM/C/EXMP$ ./gcc-ext 0
00 ---------------------------------------
вложенные функции GCC:
до : 1 , -2 , 3 , -4 , 5 , -6 , 7
после : 0 , 9 , 4 , 25 , 16 , 49 , 36
------------------------------------------
В Clang это вызывает синтаксическую ругань.

Достаточно приятное расширение GCC. Возможно Clang его тоже проглотит, но при каких-то опциях запуска?
Вложения
gcc-ext.c
(4.05 КБ) 388 скачиваний

Аватара пользователя
Olej
Писатель
Сообщения: 21338
Зарегистрирован: 24 сен 2011, 14:22
Откуда: Харьков
Контактная информация:

Re: Clang

Непрочитанное сообщение Olej » 07 янв 2014, 18:24

Вот интересное обсуждение сравнения GCC с Clang: Сравнение скорости кода компиляторов С++ (gcc/icc/clang)- развёрнутое во времени с 10.05.2012 и по 05.01.2014 (т.е. на позавчера ;-) ).

Судя по обсуждению, при всей, естественной, настороженности к Clang - к 12.2013 (версия Clang 3.2) по оптимизации системы почти сравнялись.

Аватара пользователя
Olej
Писатель
Сообщения: 21338
Зарегистрирован: 24 сен 2011, 14:22
Откуда: Харьков
Контактная информация:

Re: Clang

Непрочитанное сообщение Olej » 11 сен 2014, 18:49

Olej писал(а): Интереснее дальнейшие шаги в том же направлении:
- назначить Clang компилятором по умолчанию для IDE Visual Studio;
- научить его (Visual Studio) использовать новую библиотеку libc++;
- ... ну, и предварительно собрать ту же libc++ в Visual Studio используя Clang;
Виктория писал(а):GnuWin32 - это уже не совсем идеальный эксперимент!
Вот, якобы, плагин, который позволяет установить Clang компилятором по умолчанию в MS VisualStudio: ClangVSx
Add-in that allows easy use of Clang compiler from inside Visual Studio 2010 or 2012, replacing the MSVC compiler when building C++ projects.
И авторская страничка "как это сделать": ClangVSx
A Visual Studio AddIn that lets users play with the Clang C/C++ compiler from within the VS IDE. Designed to translate MSVC C/C++ compiler options into arguments that Clang understands while retaining and executing the rest of the build pipeline.

Аватара пользователя
Olej
Писатель
Сообщения: 21338
Зарегистрирован: 24 сен 2011, 14:22
Откуда: Харьков
Контактная информация:

Re: Clang

Непрочитанное сообщение Olej » 24 сен 2014, 13:21

Olej писал(а): Гораздо лучше дела с Clang, похоже, обстоят в репозитариях Debian 7.0: поставил из репозитария, проверил - все тестовые примеры работают сразу и без артефактов.
Кроме Clang, в проекте LLVM, интерес представляет и его "младший брат" Cling - интерпретатор для языка C++.
CLing (в отличие от CLang) в репозитариях Linux нет (в тех где я смотрел).
Но проще всего взять бинарную сборку на странице CERN: CERN PH-SFT Builds. Здесь сборки CERN и CLing и CLang и др. утилит... "от корня" - т.е. просто раскидать по каталогам.
Но можно Cling использовать просто из рабочего распакованного архива.

Аватара пользователя
Olej
Писатель
Сообщения: 21338
Зарегистрирован: 24 сен 2011, 14:22
Откуда: Харьков
Контактная информация:

Re: Clang

Непрочитанное сообщение Olej » 04 фев 2018, 17:56

Olej писал(а): Гораздо лучше дела с Clang, похоже, обстоят в репозитариях Debian 7.0: поставил из репозитария, проверил - все тестовые примеры работают сразу и без артефактов.
Так вот происходило (было проверено) при установке вот этой сборки Debian: Экспериментальная сборка дистрибутива Debian Wheezy + MATE.
Опять возникла необходимость сборки приложений Clang++ с использованием (альтернативно) C++ библиотеки а). libstdc++.so - это библиотека GCC и б). libc++.so - это новая библиотека из проекта LLVM (оттуда же, откуда и сам Clang).

Это нужно и важно для разборок с языком Swift от Apple: Swift под Linux.

Для этого простейшее приложение-пробник собираем так и так ... вот такое "приложение":

Код: Выделить всё

#include <iostream>
using namespace std;

int main( int argc, char **argv ) {
   cout << "Hello Clang!" << endl;
}
А проверку того, что с библиотеками всё ОК, делаем 2 параллельные сборки:

Код: Выделить всё

olej@olej-VirtualBox ~/2018_WORK/own.BOOKs/ManyLang/swift $ clang++ -stdlib=libc++ hello.cc -o hello2
olej@olej-VirtualBox ~/2018_WORK/own.BOOKs/ManyLang/swift $ clang++ -stdlib=libstdc++ hello.cc -o hello1
Как видно по размеру - это совершенно разные приложения...

Код: Выделить всё

olej@olej-VirtualBox ~/2018_WORK/own.BOOKs/ManyLang/swift $ ./hello1
Hello Clang!
olej@olej-VirtualBox ~/2018_WORK/own.BOOKs/ManyLang/swift $ ./hello2
Hello Clang!
Но это всё - забегая вперёд! А прежде нужно установить всё необходимое, и сделаю я это в новой, чистой системе...

Аватара пользователя
Olej
Писатель
Сообщения: 21338
Зарегистрирован: 24 сен 2011, 14:22
Откуда: Харьков
Контактная информация:

Re: Clang

Непрочитанное сообщение Olej » 04 фев 2018, 18:12

Olej писал(а):Но это всё - забегая вперёд! А прежде нужно установить всё необходимое, и сделаю я это в новой, чистой системе...
Чистая система, только установлена:

Код: Выделить всё

olej@olej-VirtualBox ~/2018_WORK/own.BOOKs/ManyLang/swift $ lsb_release -a
No LSB modules are available.
Distributor ID:	LinuxMint
Description:	Linux Mint 18.3 Sylvia
Release:	18.3
Codename:	sylvia
Начали...

Код: Выделить всё

olej@olej-VirtualBox ~ $ gcc --version
gcc (Ubuntu 5.4.0-6ubuntu1~16.04.5) 5.4.0 20160609
Copyright (C) 2015 Free Software Foundation, Inc.
This is free software; see the source for copying conditions.  There is NO
warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.

olej@olej-VirtualBox ~ $ g++ --version
Программа 'g++' на данный момент не установлена. Вы можете установить её, выполнив:
sudo apt install g++
GCC С++ в системе нет!
Дополняем! :

Код: Выделить всё

olej@olej-VirtualBox ~ $ sudo apt install g++
Построение дерева зависимостей
Чтение информации о состоянии… Готово
Будут установлены следующие дополнительные пакеты:
  cpp-5 g++-5 gcc-5 gcc-5-base libasan2 libatomic1 libc-dev-bin libc6-dev libcc1-0 libcilkrts5 libgcc-5-dev libgfortran3
  libgomp1 libitm1 liblsan0 libmpx0 libquadmath0 libstdc++-5-dev libstdc++6 libtsan0 libubsan0
Предлагаемые пакеты:
  gcc-5-locales g++-multilib g++-5-multilib gcc-5-doc libstdc++6-5-dbg gcc-5-multilib libgcc1-dbg libgomp1-dbg
  libitm1-dbg libatomic1-dbg libasan2-dbg liblsan0-dbg libtsan0-dbg libubsan0-dbg libcilkrts5-dbg libmpx0-dbg
  libquadmath0-dbg glibc-doc libstdc++-5-doc
НОВЫЕ пакеты, которые будут установлены:
  g++ g++-5 libc-dev-bin libc6-dev libstdc++-5-dev
Пакеты, которые будут обновлены:
  cpp-5 gcc-5 gcc-5-base libasan2 libatomic1 libcc1-0 libcilkrts5 libgcc-5-dev libgfortran3 libgomp1 libitm1 liblsan0
  libmpx0 libquadmath0 libstdc++6 libtsan0 libubsan0
обновлено 17, установлено 5 новых пакетов, для удаления отмечено 0 пакетов, и 65 пакетов не обновлено.
Необходимо скачать 32,2 MБ архивов.
После данной операции, объём занятого дискового пространства возрастёт на 53,1 MB.
Хотите продолжить? [Д/н] y
...
olej@olej-VirtualBox ~ $ g++ --version
g++ (Ubuntu 5.4.0-6ubuntu1~16.04.6) 5.4.0 20160609
Copyright (C) 2015 Free Software Foundation, Inc.
This is free software; see the source for copying conditions.  There is NO
warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.

Код: Выделить всё

olej@olej-VirtualBox ~ $ clang
Программа 'clang' на данный момент не установлена. Вы можете установить её, выполнив:
sudo apt install clang
Clang в системе нет (естественно).
Дополняем:

Код: Выделить всё

olej@olej-VirtualBox ~ $ sudo apt install clang
[sudo] пароль для olej:
Чтение списков пакетов… Готово
Построение дерева зависимостей
Чтение информации о состоянии… Готово
Будут установлены следующие дополнительные пакеты:
  clang-3.8 libclang-common-3.8-dev libclang1-3.8 libllvm3.8 libobjc-5-dev libobjc4
Предлагаемые пакеты:
  gnustep gnustep-devel clang-3.8-doc
Рекомендуемые пакеты:
  llvm-3.8-dev
НОВЫЕ пакеты, которые будут установлены:
  clang clang-3.8 libclang-common-3.8-dev libclang1-3.8 libllvm3.8 libobjc-5-dev libobjc4
обновлено 0, установлено 7 новых пакетов, для удаления отмечено 0 пакетов, и 65 пакетов не обновлено.
Необходимо скачать 37,6 MБ архивов.
После данной операции, объём занятого дискового пространства возрастёт на 159 MB.
Хотите продолжить? [Д/н] y
...
olej@olej-VirtualBox ~ $ clang++ --version
clang version 3.8.0-2ubuntu4 (tags/RELEASE_380/final)
Target: x86_64-pc-linux-gnu
Thread model: posix
InstalledDir: /usr/bin

Аватара пользователя
Olej
Писатель
Сообщения: 21338
Зарегистрирован: 24 сен 2011, 14:22
Откуда: Харьков
Контактная информация:

Re: Clang

Непрочитанное сообщение Olej » 04 фев 2018, 18:24

Olej писал(а): Дополняем! :
Сборка с C++ библиотекой GCC:

Код: Выделить всё

olej@olej-VirtualBox ~/2018_WORK/own.BOOKs/ManyLang/swift $ clang++ -xc++ -stdlib=libstdc++ hello.cc -o hellocc

olej@olej-VirtualBox ~/2018_WORK/own.BOOKs/ManyLang/swift $ ./hellocc
Hello Clang!
Сборка с C++ библиотекой LLVM:

Код: Выделить всё

olej@olej-VirtualBox ~/2018_WORK/own.BOOKs/ManyLang/swift $ clang++ -xc++ -stdlib=libc++ hello.cc -o hellocc
hello.cc:2:10: fatal error: 'iostream' file not found
#include <iostream>
         ^
1 error generated.

Не тут то было - нет такой библиотеки libc++.so!
Ищем пакет библиотеки.
Проблема здесь в том, что + в шаблоне поиска всё сбивают...

Код: Выделить всё

olej@olej-VirtualBox ~/2018_WORK/own.BOOKs/ManyLang $ apt search 'libc\+\+-dev'
p   libc++-dev                                            - LLVM C++ Standard library (development files)
p   libc++-dev:i386                                       - LLVM C++ Standard library (development files)

Код: Выделить всё

olej@olej-VirtualBox ~/2018_WORK/own.BOOKs/ManyLang $ sudo apt install libc++-dev
[sudo] пароль для olej:
Чтение списков пакетов… Готово
Построение дерева зависимостей
Чтение информации о состоянии… Готово
Будут установлены следующие дополнительные пакеты:
  libc++-helpers libc++1
НОВЫЕ пакеты, которые будут установлены:
  libc++-dev libc++-helpers libc++1
обновлено 0, установлено 3 новых пакетов, для удаления отмечено 0 пакетов, и 65 пакетов не обновлено.
Необходимо скачать 786 kБ архивов.
После данной операции, объём занятого дискового пространства возрастёт на 6.881 kB.
Хотите продолжить? [Д/н] y
...
Вот теперь всё ОК:

Код: Выделить всё

olej@olej-VirtualBox ~/2018_WORK/own.BOOKs/ManyLang/swift $ clang++ -xc++ -stdlib=libc++ hello.cc -o hellocc
olej@olej-VirtualBox ~/2018_WORK/own.BOOKs/ManyLang/swift $ ./hellocc
Hello Clang!

Ответить

Вернуться в «Программирование»

Кто сейчас на конференции

Сейчас этот форум просматривают: нет зарегистрированных пользователей и 13 гостей