Existe um comando do sistema, no Linux, que reporta o endianness?

28

Alguém sabe de um comando que informa se um sistema é Big Endian ou Little Endian, ou a melhor opção é uma técnica como esta usando Perl ou uma cadeia de comandos?

Perl

# little
$ perl -MConfig -e 'print "$Config{byteorder}\n";'
12345678

# big
$ perl -MConfig -e 'print "$Config{byteorder}\n";'
87654321

od | awk

# little
$ echo -n I | od -to2 | awk 'FNR==1{ print substr($2,6,1)}'
1

# big
$ echo -n I | od -to2 | awk 'FNR==1{ print substr($2,6,1)}'
0

Referências

por slm 31.08.2013 / 02:18

5 respostas

35

lscpu

O comando lscpu mostra (entre outras coisas):

Byte Order:            Little Endian

Sistemas conhecidos por trabalhar em

  • CentOS 6
  • Ubuntu (12.04, 12.10, 13.04, 13.10, 14.04)
  • Fedora (17,18,19)
  • ArchLinux 2012 +
  • Linux Mint Debian (portanto, assumindo também o teste Debian).

Sistemas conhecidos por não funcionar em

  • Fedora 14
  • CentOS 5 (assumindo o RHEL5 por causa disso)

Por que as aparentes diferenças entre distros?

Depois de muita escavação, descobri o porquê. Parece que a versão util-linux versão 2.19 foi a primeira versão que incluiu o recurso onde lscpu mostra a saída relatando o Endianness do seu sistema.

Como teste, compilei ambas as versões 2.18 e 2.19 no meu sistema Fedora 14 e a saída abaixo mostra as diferenças:

util-linux 2.18

$ util-linux-ng-2.18/sys-utils/lscpu 
Architecture:          x86_64
CPU op-mode(s):        32-bit, 64-bit
CPU(s):                4
Thread(s) per core:    2
Core(s) per socket:    2
CPU socket(s):         1
NUMA node(s):          1
Vendor ID:             GenuineIntel
CPU family:            6
Model:                 37
Stepping:              5
CPU MHz:               1199.000
Virtualization:        VT-x
L1d cache:             32K
L1i cache:             32K
L2 cache:              256K
L3 cache:              3072K
NUMA node0 CPU(s):     0-3

util-linux 2.19

$ util-linux-2.19/sys-utils/lscpu 
Architecture:          x86_64
CPU op-mode(s):        32-bit, 64-bit
Byte Order:            Little Endian
CPU(s):                4
On-line CPU(s) list:   0-3
Thread(s) per core:    2
Core(s) per socket:    2
CPU socket(s):         1
NUMA node(s):          1
Vendor ID:             GenuineIntel
CPU family:            6
Model:                 37
Stepping:              5
CPU MHz:               2667.000
BogoMIPS:              5320.02
Virtualization:        VT-x
L1d cache:             32K
L1i cache:             32K
L2 cache:              256K
L3 cache:              3072K
NUMA node0 CPU(s):     0-3

As versões acima foram baixadas do site da kernel.org .

por 31.08.2013 / 02:23
5

Um método que encontrei nos sistemas Debian / Ubuntu é executar este comando:

$ dpkg-architecture
DEB_BUILD_ARCH=amd64
DEB_BUILD_ARCH_BITS=64
DEB_BUILD_ARCH_CPU=amd64
DEB_BUILD_ARCH_ENDIAN=little
DEB_BUILD_ARCH_OS=linux
DEB_BUILD_GNU_CPU=x86_64
DEB_BUILD_GNU_SYSTEM=linux-gnu
DEB_BUILD_GNU_TYPE=x86_64-linux-gnu
DEB_BUILD_MULTIARCH=x86_64-linux-gnu
DEB_HOST_ARCH=amd64
DEB_HOST_ARCH_BITS=64
DEB_HOST_ARCH_CPU=amd64
DEB_HOST_ARCH_ENDIAN=little
DEB_HOST_ARCH_OS=linux
DEB_HOST_GNU_CPU=x86_64
DEB_HOST_GNU_SYSTEM=linux-gnu
DEB_HOST_GNU_TYPE=x86_64-linux-gnu
DEB_HOST_MULTIARCH=x86_64-linux-gnu

Isso mostrará as palavras pouco ou grande, dependendo da arquitetura em que o sistema é composto:

$ dpkg-architecture | grep -i end
DEB_BUILD_ARCH_ENDIAN=little
DEB_HOST_ARCH_ENDIAN=little
    
por 31.08.2013 / 02:27
5

Usando python :

$ python -c "import sys;print sys.byteorder"
little

ou:

printf '' | od -dAn
1

onde 1 é para little endian e 00256 para big endian.

Ou usando uma versão perl mais curta:

$ perl -V:byteorder
byteorder='12345678';
    
por 03.04.2014 / 04:32
3

Um POSIX Shell & Solução C:

cat << EOF > foo.c

#include <endian.h>
#include <stdio.h>

int main() {
  printf("Byte Order: ");
  if (BYTE_ORDER == LITTLE_ENDIAN) 
    printf("little");
  else {
    if (BYTE_ORDER == BIG_ENDIAN)
      printf("big");
    else
      printf("unknown");
  }
  printf(" endian.\n");
  return 0;
}
EOF

gcc -D__USE_POSIX foo.c
./a.out
    
por 03.04.2014 / 04:57
0

Se você estiver em um sistema que não tenha endian.h :

#include <stdio.h>

int main() {
  int test = 0;
  char *bytes = (char *) &test;
  *bytes = 0x1;

  printf("Byte Order: ");
  if (test == 1){
    printf("little");
  }
  else {
      printf("big");
  }
  printf(" endian.\n");
  return 0;
}
    
por 29.03.2017 / 17:30