54
\$\begingroup\$

It's not too important anymore, but occasionally somebody needs to know.

Here is a simple golf: Taking no user input, tell me if the computer on which the code is run is on a 64-bit operating system, or a 32-bit operating system!

If the code is run on a 32-bit operating system, print "32", if the code is run on a 64 bit operating system, output "64". Important: Print any other non-empty string of alphanumeric characters if it's neither 32 or 64 bit.

Please note that a 32 bit program running on a computer with a 64 bit operating system should output "64". You can assume that users will use 64 bit software whenever possible.

To be eligible for entry, your code must be able to run on Windows 4.10 or newer Microsoft supported Windows systems, and at least one flavor of Linux of your choosing (so long as that flavor is gratis). Compatibility mods can be installed, so long as the program still returns the right value.

The usual rules apply.

Note: If your answer is only meant to print out 32 or 64, but not the alt case, I'll accept it, but it is not a competing answer.

I'll try and post some results of running these codes on different OSes later!

\$\endgroup\$
23
  • 5
    \$\begingroup\$ So "Please note that a 32 bit program running on a computer with a 64 bit operating system should output "64". You can assume that users will use 64 bit software whenever possible." means that if the interprettor/compiler etc is is available in both 32 bit and 64 bit, then a 32 bit OS, will always run the 32 bit version of the interpreter/etc, and the 64 bit OS will always run the 64 bit interpreter/etc. So worrying about the difference between the program being 32 or 64, and the OS being 32 or 64, is basically only a problem for languages with only 32 bit implementations. Right? \$\endgroup\$ Jun 20, 2017 at 4:33
  • 2
    \$\begingroup\$ Many solutions here would print "32" on a 64-bit OS if a 32-bit compiler was used to compile program. Is this OK? \$\endgroup\$ Jun 20, 2017 at 8:54
  • 16
    \$\begingroup\$ What in the world is "Windows 4.10"? Does that mean Windows 98? Or does it mean Windows NT 4? What do you consider to be "newer" than that? This seems an exceptionally poorly thought-out challenge. \$\endgroup\$ Jun 20, 2017 at 9:47
  • 14
    \$\begingroup\$ There is no "official windows spec", and nobody refers to Windows 98 as being "Windows 4.10". You are literally the first. So maybe instead of trying to sound cool or official by using version numbers, you should just use the actual product name. By the way, Windows 9x was never available in a 64-bit build, so is it actually legitimate for me to submit an entry that runs only on Windows 98 and just returns "32"? Seems very unfair/unsporting/uninteresting, but would technically be allowed by your rules. \$\endgroup\$ Jun 21, 2017 at 2:25
  • 3
    \$\begingroup\$ You still haven't answered the question about the Windows version. Does must be able to run on Windows 4.10 or newer mean on Windows 4.10 and all newer versions or on any single Windows version, 4.10 or newer? \$\endgroup\$
    – Dennis
    Jun 21, 2017 at 3:08

49 Answers 49

48
\$\begingroup\$

x86 machine code, 12 bytes

8c c8 83 f8 23 b0 20 75 02 00 c0 c3

Ungolfed:

getKernelBitness:
    mov eax,cs
    cmp eax,0x23 ; 32 bit process on 64 bit kernel has this selector in CS
    mov al,32
    jne kernelIs32Bit
    add al,al    ; return value in eax
kernelIs32Bit:
    ret

This function works in Linux when used in ELF32, following i386 SysV ABI, as well as in Windows/Wine when used in PE32, following stdcall calling convention.

\$\endgroup\$
5
  • \$\begingroup\$ Actually one can reduce byte count even more if following another approach. \$\endgroup\$
    – Ruslan
    Jun 22, 2017 at 15:41
  • \$\begingroup\$ what would this theoretically do in a non 32/64 bit environment? \$\endgroup\$
    – tuskiomi
    Jun 26, 2017 at 13:35
  • 1
    \$\begingroup\$ @tuskiomi In any case, this code will still return either 32 or 64. The only difference of interpreting this byte sequence in 16-bit mode will be a change of mnemonics from eax to ax. So, if the selector in cs happens to be 0x23, the result will be 64, otherwise 32. \$\endgroup\$
    – Ruslan
    Jun 26, 2017 at 13:44
  • \$\begingroup\$ this looks specific to two particular operating-systems, though. You could easily have a 32-bit system with cs=0x23. See instead my 8-byte answer that targets the CPU instead. \$\endgroup\$ Nov 11, 2017 at 23:51
  • \$\begingroup\$ @peterferrie yeah, that's why I have another answer. But yours does outgolf it by 2 bytes. \$\endgroup\$
    – Ruslan
    Nov 12, 2017 at 6:47
45
\$\begingroup\$

x86 Assembly (polyglot), 13 bytes

Bytecode:

31 c0 b4 80 48 70 05 04 40 83 e0 60 c3

Defines a function which returns 32 if interpreted as 32-bit, 64 if 64-bit, and 32767 if 16-bit.

I wanted to make a polyglot which ran on Windows and Linux, but this is a lot harder than I thought. As it is I'm not sure there's even any way to print a value on non-16-bit Windows without linking.

Explanation

This code uses two tells to determine the architecture it is running on. The first is the instruction 0x48—on 16 and 32 bits, this is dec %eax, but on 64 bits, it is an instruction-size prefix. The second tell is the same instruction, however, when we execute it on the value 0x8000, the most significant bit is flipped only if the register size is 16 bits, setting the overflow flag and letting us use jo.

In 16 bits, this code is interpreted as the following:

   0:   31 c0                   xor    %ax,%ax    /* 0x0000 */
   2:   b4 80                   mov    $0x80,%ah  /* 0x8000 */
   4:   48                      dec    %ax        /* 0x7fff */
   5:   70 05                   jo c              /* taken  */
   7:   04 40                   add    $0x40,%al
   9:   83 e0 60                and    $0x60,%ax
   c:   c3                      ret               /* 0x7fff */

In 32 bits, this code is interpreted as the following:

   0:   31 c0                   xor    %eax,%eax   /* 0x00000000 */
   2:   b4 80                   mov    $0x80,%ah   /* 0x00008000 */
   4:   48                      dec    %eax        /* 0x00007fff */
   5:   70 05                   jo c               /* not taken  */
   7:   04 40                   add    $0x40,%al   /* 0x00007f3f */
   9:   83 e0 60                and    $0x60,%eax  /* 0x00000020 */
   c:   c3                      ret

In 64 bits, this code is interpreted as the following:

   0:   31 c0                   xor    %eax,%eax   /* 0x00000000 */
   2:   b4 80                   mov    $0x80,%ah   /* 0x00008000 */
   4:   48 70 05                rex.W jo c         /* not taken  */
   7:   04 40                   add    $0x40,%al   /* 0x00008040 */
   9:   83 e0 60                and    $0x60,%eax  /* 0x00000040 */
   c:   c3                      ret
\$\endgroup\$
9
  • \$\begingroup\$ This is actually probably in the lead, very nice \$\endgroup\$
    – tuskiomi
    Jun 21, 2017 at 16:36
  • 1
    \$\begingroup\$ A very neat idea, but as implemented, this will return the wrong value if assembled as a 32-bit binary and run on a 64-bit operating system. \$\endgroup\$ Jun 21, 2017 at 17:26
  • 1
    \$\begingroup\$ @CodyGray from the rules: You can assume that users will use 64 bit software whenever possible. I suppose this also means that for functions we can assume that the caller code is 64 bit whenever possible. \$\endgroup\$
    – Ruslan
    Jun 22, 2017 at 19:30
  • \$\begingroup\$ Ah, I suppose that's a fair interpretation, @Ruslan. And I see you have already posted the answer I had in mind, were it not for this issue. :-) You've got my upvote. \$\endgroup\$ Jun 23, 2017 at 6:22
  • \$\begingroup\$ does the byte 48 represent dec %eax in 16-bit mode? \$\endgroup\$
    – phuclv
    Jun 24, 2017 at 13:50
33
\$\begingroup\$

Mathematica, 17 bytes

$SystemWordLength
\$\endgroup\$
8
  • 13
    \$\begingroup\$ Of course there's a builtin! \s (+1) \$\endgroup\$
    – tuskiomi
    Jun 19, 2017 at 20:35
  • \$\begingroup\$ Shouldn't you either add an & or specify that this is in the REPL? \$\endgroup\$ Jun 19, 2017 at 20:48
  • 5
    \$\begingroup\$ @LegionMammal978 "If the code is ran on a 32-bit operating system, print "32", if the code is ran on a 64 bit operating system, output "64". Print any (other) non-empty string of alphanumeric characters if it's neither." Not "provide a function that, when run, does this"; just "do this". \$\endgroup\$ Jun 19, 2017 at 21:41
  • 17
    \$\begingroup\$ @PatrickStevens: If the question doesn't specify what form a submission should take, it's a program or function, but not a snippet, by default. \$\endgroup\$
    – user62131
    Jun 19, 2017 at 22:16
  • 3
    \$\begingroup\$ @ais523 I would argue there is no distinction in Mathematica between programs, functions, and snippets. Everything is just an expression. \$\endgroup\$
    – user61980
    Jun 21, 2017 at 16:05
22
\$\begingroup\$

Julia 14 13 bytes

n->8sizeof(1)

Explain:

  • Anon function, taking anything (including nothing) returning an integer 32, or 64
  • Integer literals are of type Int which depending if 32 bit or 64 bit, is either an Int32 or an Int64 (the 1 could be any digit)
  • placing a number before a function call does a juxtaposition multiplication
  • This is basically a minified version of the code for Sys.WORD_SIZE, used in rahnema1's answer

Other fun answer is ()->"$(Int)"[4:5], but I can't get the count down on that one.


-1 thanks to @Roman Gräf

\$\endgroup\$
1
21
\$\begingroup\$

Boot Loaders

Did you know that GRUB and IPXE both have Turing complete programming languages accessible at run-time? The Syslinux family of boot loaders don't but they can do this.

IPXE, 36 bytes

#!ipxe
cpuid --ext 29 && echo 64 || echo 32

the first line is needed if the script is run remotely, but not if typed directly at the command line.

GRUB, 42 bytes

if cpuid -l ; then
echo 64
else
echo 32
fi

Syslinux, 186 bytes

This takes three files the first is syslinux.cfg (or isolinux.cfg, etc.).

label a
  kernel ifcpu64.c32
  append s -- t

label s
  kernel menu.c32
  append s.cfg

label t
  kernel menu.c32
  append t.cfg

default a
prompt 0
timeout 0

and t.cfg

menu title 32

ans s.cfg

menu title 64

For this one the hard part is that syslinux does not have any simple text display capabilities, so the menu is abused.

\$\endgroup\$
11
  • \$\begingroup\$ I'm not sure if you can tell the os resolution with a boot loader, but i like the idea \$\endgroup\$
    – tuskiomi
    Jun 20, 2017 at 22:13
  • \$\begingroup\$ It checks the cpu and is used to select the right operating system. This is basically golfed code from my unboot project. \$\endgroup\$
    – hildred
    Jun 20, 2017 at 22:17
  • 2
    \$\begingroup\$ So it changes the os based on the architecture. Thinking outside the box. I like. \$\endgroup\$
    – tuskiomi
    Jun 20, 2017 at 22:18
  • \$\begingroup\$ What's the bytecount? \$\endgroup\$
    – Restioson
    Jun 22, 2017 at 15:45
  • 1
    \$\begingroup\$ @hildred I believe it would be more readable if you used ## iPXE, 36 bytes instead of ### ipxe 36 \$\endgroup\$
    – Maya
    Jun 22, 2017 at 16:45
19
\$\begingroup\$

julia, 20 17 16 bytes

n->Sys.WORD_SIZE

*Thanks to @LyndonWhite saved 3 bytes *Thanks to @RomanGräf saved a byte

Previous answers:

()->Sys.WORD_SIZE
print(Sys.WORD_SIZE)

Try it online!

\$\endgroup\$
3
14
\$\begingroup\$

JavaScript (Node.js), 24 bytes

_=>process.arch.slice(1)

This is a function and returns '32', '64', or if neither 'rm'.

\$\endgroup\$
6
  • \$\begingroup\$ +1, but I suppose a 64bit arch could be running a 32bit OS though \$\endgroup\$
    – Octopus
    Jun 19, 2017 at 22:35
  • 1
    \$\begingroup\$ Gives me '32' on 32-bit Windows, so it does appear to work. \$\endgroup\$
    – Ken Y-N
    Jun 20, 2017 at 6:16
  • 5
    \$\begingroup\$ You can shave off 7 bytes if you're using the REPL and os instead of process: os.arch().slice(1) \$\endgroup\$
    – GilZ
    Jun 20, 2017 at 10:21
  • \$\begingroup\$ This returns the OS architecture reported to the process, not the actual OS architecture. So this does not work on Linux. (Punch "setarch" into your favorite search engine.) \$\endgroup\$ Jun 21, 2017 at 23:24
  • \$\begingroup\$ @DavidSchwartz it works fine on my linux box unless I'm misunderstanding, but on PPCG we can assume an unmodified environment in terms of user changing the arch \$\endgroup\$
    – Downgoat
    Jun 22, 2017 at 0:06
13
\$\begingroup\$

C, 33 31 29 23 bytes

f(){return sizeof&f*8;}

Thanks to commenters @ceilingcat and @Dennis for golfing tips!

\$\endgroup\$
11
  • 13
    \$\begingroup\$ It also says that the usual code golf rules apply, and returning from a function is part of our defaults for I/O. \$\endgroup\$
    – Dennis
    Jun 19, 2017 at 21:42
  • 11
    \$\begingroup\$ Isn't that going to depend on whether you compile as a 32 or 64 bit program? \$\endgroup\$
    – Ken Y-N
    Jun 20, 2017 at 4:35
  • 4
    \$\begingroup\$ This doesn't comply with the requirements. "Please note that a 32 bit program running on a computer with a 64 bit operating system should output "64"." This tells you how the program was compiled, not what the OS is. \$\endgroup\$ Jun 21, 2017 at 23:24
  • 2
    \$\begingroup\$ @DavidSchwartz "You can assume that users will use 64 bit software whenever possible." \$\endgroup\$ Jun 22, 2017 at 12:16
  • 3
    \$\begingroup\$ Sorry to say that but sizeof is evaluated at compile time. So if you compile a 32 bit exe and run it on a 64 bit machine, it will ouput 32 while it should output 64 (stackoverflow.com/questions/2615203/…). Nice idea though ! \$\endgroup\$
    – Dinaiz
    Jun 23, 2017 at 1:14
10
\$\begingroup\$

Python 2, 52, 48, 42 41 bytes

from struct import*;print calcsize("P")*8

Thanks to totallyhuman!

\$\endgroup\$
12
  • \$\begingroup\$ zoom! across the line in under a minute. \$\endgroup\$
    – tuskiomi
    Jun 19, 2017 at 20:16
  • \$\begingroup\$ I'm going to hold off on testing this until i'm home, but i'm not sure this prints out "32" and "64", but other cases i'm confident. \$\endgroup\$
    – tuskiomi
    Jun 19, 2017 at 20:21
  • \$\begingroup\$ @tuskiomi, this prints "32bit" or "64bit" \$\endgroup\$
    – Daniel
    Jun 19, 2017 at 20:21
  • 1
    \$\begingroup\$ from struct import*;print calcsize("P")*8 is shorter. \$\endgroup\$ Jun 19, 2017 at 20:42
  • 12
    \$\begingroup\$ If you run this on 32-bit Python in a 64-bit OS, I think this will lie to you. Most other answers also seem sensitive to that anyways... \$\endgroup\$
    – Nick T
    Jun 19, 2017 at 22:02
10
\$\begingroup\$

Java 8, 45 bytes

()->System.getProperty("sun.arch.data.model")
\$\endgroup\$
16
  • \$\begingroup\$ @Dopapp What (s)he means is that this is a snippet, not a program or function. In Java 8, this should work: n=>System.getProperty("os.arch") \$\endgroup\$ Jun 19, 2017 at 20:25
  • \$\begingroup\$ @NoOneIsHere, oh thank you that went way over my head \$\endgroup\$
    – Daniel
    Jun 19, 2017 at 20:26
  • 2
    \$\begingroup\$ "If the code is ran on a 32-bit operating system, print "32", if the code is ran on a 64 bit operating system, output "64". Print any (other) non-empty string of alphanumeric characters if it's neither.". This doesn't do that at all... \$\endgroup\$ Jun 19, 2017 at 22:54
  • 4
    \$\begingroup\$ Can you get Java 8 for Windows 98 (v4.10) ? \$\endgroup\$ Jun 20, 2017 at 6:11
  • 4
    \$\begingroup\$ @TessellatingHeckler Java 8 requires "i586" (whatever that means). The entry says: "your code must be able to run on Windows 4.10 or newer", not "your code must be able to run on Windows 4.10 and newer". It runs on a Windows newer. \$\endgroup\$ Jun 20, 2017 at 7:44
10
\$\begingroup\$

PowerShell, 16 bytes

8*[IntPtr]::Size

Gets the pointer size in bytes, multiplies by 8 to get bits.

\$\endgroup\$
7
  • \$\begingroup\$ -1 because your code must be able to run on Windows 4.10 or newer \$\endgroup\$ Jun 20, 2017 at 5:06
  • 13
    \$\begingroup\$ @ub3rst4r or newer, not and newer. I'm willing to bet a good chunk of these answers are difficult, at best, to run on a long-unsupported version of Windows. It's also unreasonable to expect people to test on 98 of all OSes - it's not even easy to install in a VM these days (trust me, I've tried. Not gonna run on KVM, and it has interesting interactions with VBox display adapters). (Nor does it even have a concept of 64-bit... that's a truly ridiculous requirement.) \$\endgroup\$
    – Bob
    Jun 20, 2017 at 6:37
  • 1
    \$\begingroup\$ @ub3rst4r I doubt that all of the interpreted programming languages here have an implementation working on Windows 4.10! \$\endgroup\$ Jun 20, 2017 at 8:51
  • 1
    \$\begingroup\$ This looks like it fails if it's a 32-bit powershell on a 64-bit OS. \$\endgroup\$
    – Callie J
    Jun 21, 2017 at 9:28
  • \$\begingroup\$ @ChrisJ At least on Win10 and Win2012 R2 it returns the proper result from x86 PowerShell. Haven't tested on Linux. \$\endgroup\$
    – Booga Roo
    Jun 21, 2017 at 18:29
9
\$\begingroup\$

Perl 6, 17 bytes

say $*KERNEL.bits

Try it


There is a related $?BITS which contains the number of bits that a native int has in the runtime.

say $?BITS

Try it

\$\endgroup\$
8
\$\begingroup\$

Windows CMD, 56 52 bytes (thanks Bob!)

if EXIST "%ProgramFiles(x86)%" (echo 64)else echo 32

Still surprisingly lengthy - longest so far!

\$\endgroup\$
20
  • 1
    \$\begingroup\$ Actually, %windir%\SysWOW64 is even shorter, I think... \$\endgroup\$
    – Bob
    Jun 20, 2017 at 5:07
  • 7
    \$\begingroup\$ "must be able to run on Windows 4.10 or newer, and at least one flavor of Linux of your choosing" - which flavour of Linux for this? \$\endgroup\$ Jun 20, 2017 at 6:13
  • 1
    \$\begingroup\$ @TessellatingHeckler if you install Wine...? \$\endgroup\$
    – Ken Y-N
    Jun 20, 2017 at 6:14
  • 1
    \$\begingroup\$ What about using shorthand? if EXIST "c:\Progra~3" (echo 64)else echo 32 By default you have ProgramData and Program Files so if a third exists, we should be 64 \$\endgroup\$
    – Marie
    Jun 20, 2017 at 20:09
  • 3
    \$\begingroup\$ What will this print for an 8-bit OS? \$\endgroup\$
    – tuskiomi
    Jun 21, 2017 at 13:43
7
\$\begingroup\$

Ruby, 22 bytes

p [?a].pack(?p).size*8

["any string"].pack("p") returns a string whose bytes correspond to the pointer that pointed towards "any string", and is 8 characters if the OS is 64-bit, or 4 characters if the OS is 32-bit.

\$\endgroup\$
2
  • \$\begingroup\$ Since this is using the pointer size, this will print 32-bit when the Ruby interpreter is a 32-bit binary on a 64-bit OS. So misses a rule. \$\endgroup\$
    – DarkDust
    Jun 20, 2017 at 11:36
  • 1
    \$\begingroup\$ @DarkDust You can assume that users will use 64 bit software whenever possible. So 64-bit users will be assumed to be running 64-bit Ruby. \$\endgroup\$
    – Value Ink
    Jun 20, 2017 at 17:12
7
\$\begingroup\$

C, Win32 API, 103 183 bytes

#include <windows.h>
typedef int(WINAPI*F)(HANDLE,int*);b;main(){F f=GetProcAddress(GetModuleHandle("kernel32"),"IsWow64Process");return(f!=0&&f(GetCurrentProcess(),&b)&&!b)?32:64;}

Actually there are more than 2 cases here. Let's examine them

  • The easiest: IsWow64Process does not exist: We are on a 32 bit OS

For the next two cases we need to have the knowledge that our binary will be a 32 bit executable. And this description of what will be out into the out parameter of IsWow64Process

A pointer to a value that is set to TRUE if the process is running under WOW64. If the process is running under 32-bit Windows, the value is set to FALSE. If the process is a 64-bit application running under 64-bit Windows, the value is also set to FALSE.

That leaves us with two additional cases:

  • IsWow64Process exists, and yields TRUE -> We are on a 64 bit machine
  • IsWow64Process exists, and yields FALSE -> We are on a 32 bit machine

We don't wory about the part where a 64-bit application on a 64-bit Windows yields FALSE. As we know that our application is 32-bit

Oh and there is one additional case that is not covered by this challenge and should be rare anyways:

  • IsWow64Process exists, but it fails: We default to 32-bit machine.

This should cover most Windows NT Operating Systems. Have only tested on Win10 64-Bit, Win 7 64-Bit, Win 8.1 32-Bit and WinXP SP1 32-Bit


Original answer:

#include<windows.h>
main(){return GetProcAddress(GetModuleHandle("Kernel32"),"IsWow64Process")?64:32;}

To be sure we need to distinguish only 2 cases

  • IsWow64Process does not exist in kernel32.dll => We are on a 32 bit machine.

  • IsWow64Process does exist => We are on a 64 bit machine.

The actual value provided by IsWow64Process is irrelevant for this challange, since we want the binary to be 32bit in any case.

Unlike most of the answers, this doesn't rely on the binary itself being compiled on the machine that it's executed on.

If I knew a shorter function that is present only on 64bit and not 32bit machines, I could shorten the answer.

\$\endgroup\$
10
  • 2
    \$\begingroup\$ Drop the .dll from the module name string. Not only is this good for golfing, but it's actually a better practice in normal use, too. Also, for golfing purposes, you can drop the space after #include. \$\endgroup\$ Jun 20, 2017 at 15:00
  • \$\begingroup\$ Thanks, I actually wanted to reduce the whole thing by just looking for a module that can be found on 64bit but not on 32bit. I'm still looking. Sadly (for this purpose) there is no module called WoW64. \$\endgroup\$
    – MrPaulch
    Jun 20, 2017 at 15:03
  • \$\begingroup\$ There is actually a wow64.dll and Wow64Win.dll, but I have never tried to call GetModuleHandle with those. The problem, though, is that they would only be loaded for a 32-bit process running on a 64-bit machine, not for a 64-bit process running on a 64-bit machine. \$\endgroup\$ Jun 20, 2017 at 15:05
  • \$\begingroup\$ I have. They return 0 even on a 64bit machine. Makes sense actually. They don't exist to be linked with directly. The system takes care of the redirection during runtime. \$\endgroup\$
    – MrPaulch
    Jun 20, 2017 at 15:07
  • \$\begingroup\$ Ooh, problem though. From the SDK documentation: "Note that this technique is not a reliable way to detect whether the operating system is a 64-bit version of Windows because the Kernel32.dll in current versions of 32-bit Windows also contains this function." \$\endgroup\$ Jun 20, 2017 at 15:08
7
\$\begingroup\$

C#, 60 50 bytes

_=>System.Environment.Is64BitOperatingSystem?64:32

Thanks @TheLethalCoder

\$\endgroup\$
7
  • 1
    \$\begingroup\$ Welcome to the site! :) \$\endgroup\$
    – DJMcMayhem
    Jun 20, 2017 at 6:22
  • 4
    \$\begingroup\$ Save 4 bytes if you remove 'Line' \$\endgroup\$
    – John
    Jun 20, 2017 at 10:58
  • 1
    \$\begingroup\$ can also remove 'Environment.' and 'console.' assuming use of using static System.Environment; and using static System.Console; \$\endgroup\$
    – John
    Jun 20, 2017 at 11:00
  • 1
    \$\begingroup\$ also, change WriteLine to Write \$\endgroup\$ Jun 20, 2017 at 13:20
  • 7
    \$\begingroup\$ @John Last time I checked, imports must be included and so would add to the byte count \$\endgroup\$
    – Ceshion
    Jun 20, 2017 at 18:02
6
\$\begingroup\$

R, 16 bytes

.Machine[[18]]*8

Returns the pointer size.

\$\endgroup\$
3
  • 1
    \$\begingroup\$ Like all pointer-size solutions, this will print the wrong result when the program is a 32-bit binary running on a 64-bit OS. \$\endgroup\$
    – DarkDust
    Jun 20, 2017 at 11:39
  • 1
    \$\begingroup\$ @DarkDust R is interpreted, and we can assume the user uses 64-bit software where possible, so also a 64-bit interpreter. IMHO, the rule only applies to compiled languages \$\endgroup\$
    – Maya
    Jun 22, 2017 at 16:39
  • \$\begingroup\$ @NieDzejkob That is the exact same logic I have used for my answer in PHP when someone else put the same type of comment in response to my answer, I wish others read the same from the question as we have on assuming users will use 64-bit software where possible with interpreted languages. \$\endgroup\$
    – Bja
    Jun 24, 2017 at 8:03
6
\$\begingroup\$

Perl, 18 15 18 bytes

say length pack p8
\$\endgroup\$
4
  • \$\begingroup\$ I get 64␤ on my 32 bit computer, because perl was built with a 64bit IV. You'll find this is usually the case when running on 32bit version of Windows. \$\endgroup\$ Jun 20, 2017 at 18:39
  • \$\begingroup\$ @BradGilbertb2gills I reverted the code to the previous version; this one should work even in this case. Let me know if it still doesn’t work, I’ll delete my answer. \$\endgroup\$
    – Grimmy
    Jun 20, 2017 at 18:54
  • 1
    \$\begingroup\$ That works correctly. \$\endgroup\$ Jun 20, 2017 at 19:21
  • \$\begingroup\$ Seems wrong on HP 9000/785. Gives 32. But I do not think there were any 32-bit HP/PA-RISC CPUs. \$\endgroup\$
    – Ole Tange
    Jun 25, 2017 at 12:55
6
\$\begingroup\$

PHP, 18 Bytes

<?=PHP_INT_SIZE*8;

This correctly handles all of the cases of 32, 64 and other bit CPUs provided that PHP_INT_SIZE is correct, it will show the precise size of the CPU no matter what CPU PHP is running on!

If PHP is running on

32-bit OS PHP_INT_SIZE == 4,

64-bit OS PHP_INT_SIZE == 8,

16-bit OS PHP_INT_SIZE == 2 (theoretically)

8-bit OS PHP_INT_SIZE == 1 (again theoretically)

128-bit OS PHP_INT_SIZE == 16 (Not yet achieved but possible)

\$\endgroup\$
2
  • 2
    \$\begingroup\$ that constant has the size of the OS where PHP was built, not run \$\endgroup\$
    – Einacio
    Jun 22, 2017 at 1:44
  • 3
    \$\begingroup\$ @Einacio Yes, but in the initial challenge the poster wrote "You can assume that users will use 64 bit software whenever possible", Therefore if the OS is 64-bit then the version of PHP running on the OS would have to be assumed to be 64-bit! (Note: I don't see this as a loophole just pure logic based off of the initial challenge.) \$\endgroup\$
    – Bja
    Jun 22, 2017 at 7:26
6
\$\begingroup\$

x86 machine code, 8 bytes

31 C0 B0 40 48 24 60 C3

Ungolfed:

31 c0    xor eax,eax
b0 40    mov al, 0x40
48       dec al — in 32-bit mode; "REX.W" in 64-bit mode (ignored)
24 60    and al, 0x60
c3       ret

If compiled as a 64-bit executable, it returns 64 in eax, and if compiled as 32-bit, then returns 32 — regardless of the OS.

This answer relies on the rules saying:

You can assume that users will use 64 bit software whenever possible.

\$\endgroup\$
2
  • \$\begingroup\$ While this is an interesting approach, how can it be written into a program in such a way that it can actually be executed? Every method I can think of executing binary code other than writing your own loader function uses files that are specific to 64-bit or 32-bit code. Therefore, you'll need two copies of this code in order to actually run... \$\endgroup\$
    – Jules
    Jun 24, 2017 at 22:48
  • \$\begingroup\$ @Jules You can put it as inline assembly into a high-level language program, like here. Then you just need to use your platform-native compiler with its default options, and you'll get the bitness. \$\endgroup\$
    – Ruslan
    Jun 25, 2017 at 5:52
4
\$\begingroup\$

C# (29 bytes)

Console.Write(IntPtr.Size*8);
\$\endgroup\$
2
  • 10
    \$\begingroup\$ Like all pointer-size solutions, this will print the wrong result when the program is a 32-bit binary running on a 64-bit OS. \$\endgroup\$
    – DarkDust
    Jun 20, 2017 at 11:39
  • 1
    \$\begingroup\$ Need to specify that this is compiled for "AnyCPU" with the "Prefer 32-bit" checkbox unchecked. \$\endgroup\$ Jun 23, 2017 at 17:00
4
\$\begingroup\$

PowerShell, 17 52 bytes

try{32+32*((gci \*`))-or(arch)[-1]-eq52)}catch{32}

Returns 64 if either of the following is true:

  • You have a directory on your current drive with a filename ending in a close paren, the idea being to detect Program Files (x86).
  • arch returns a string ending in 4 (ASCII 52), like x86_64, as opposed to e.g. i686.

The try-catch is intended to circumvent the error you get if gci returns nothing and you don't have an arch. I haven't found a shorter way to do it so far. gci is used over ls because on Linux, ls will produce a visible error.

This version should detect whether the OS is 64-bit rather than just PowerShell, and is tested to work on Windows and Linux. For Mac support, replace arch with uname -m.

Previous Windows-only version: -!(ls \*`))*32+64

\$\endgroup\$
4
  • \$\begingroup\$ what linux distro does this run on? \$\endgroup\$
    – tuskiomi
    Jun 20, 2017 at 18:51
  • \$\begingroup\$ @tuskiomi Oh, my bad - I see what you mean. Didn't read the challenge properly. Should I delete the answer? \$\endgroup\$
    – Andy C.
    Jun 20, 2017 at 19:17
  • \$\begingroup\$ If you know it'll work with WINE, you should keep it. \$\endgroup\$
    – tuskiomi
    Jun 20, 2017 at 19:20
  • \$\begingroup\$ @tuskiomi At the very least Ubuntu 14.04, 16.04, RHEL7, CentOS7 and some version of SUSE: github.com/PowerShell/PowerShell/releases \$\endgroup\$
    – Xudonax
    Jun 24, 2017 at 17:16
4
\$\begingroup\$

Swift 4 REPL/Playground, 12 bytes

Int.bitWidth

Int is word sized, acting like either Int32 or Int64 depending on the system.

\$\endgroup\$
2
  • \$\begingroup\$ Isn't this a code-snip it, so it should print? Or does saying you are using the REPL get around that restriction? \$\endgroup\$ Jun 21, 2017 at 1:28
  • 1
    \$\begingroup\$ That's up to the judges. The REPL usage isn't very common, but Swift Playgrounds are very popular (especially on iPad). Personally, I think it's fair game. People design custom programming languages for golfing that implicitly print values, and this is no different \$\endgroup\$
    – Alexander
    Jun 21, 2017 at 5:25
4
\$\begingroup\$

Ruby, 10 bytes

p 0.size*8

While Ruby can use integers of any length, internally it stores the values that fit in a machine word as Fixnum. The method Fixnum#size always return the length in bytes of a machine word.

The Fixnum class was removed in Ruby 2.4.0, its functionality was included in class Integer. The code stands.

\$\endgroup\$
4
\$\begingroup\$

Shell, 26 bytes

uname -m|awk \$0=/_/?64:32
\$\endgroup\$
7
  • \$\begingroup\$ You can use arch instead of uname -m. \$\endgroup\$
    – Dennis
    Jun 20, 2017 at 6:29
  • 1
    \$\begingroup\$ @Dennis Not necessarily. On macos: uname -m -> x86_64, but arch -> i386. Because macos :( Also, this is bash-specific - fails on zsh. \$\endgroup\$
    – viraptor
    Jun 20, 2017 at 9:28
  • \$\begingroup\$ @StevenPenny zsh will try to interpret the ? as a glob / single character wildcard. \$\endgroup\$
    – Doorknob
    Jun 20, 2017 at 12:43
  • \$\begingroup\$ Does this run on Windows? \$\endgroup\$
    – Ajasja
    Jun 20, 2017 at 15:03
  • \$\begingroup\$ @viraptor this is Code Golf, not a portability competition. As long as it works on Windows and at least one free Linux distribution, as the rules say, it is OK. Otherwise I could just as easily run it with linux32/setarch i386 command and break it. \$\endgroup\$
    – Ruslan
    Jun 21, 2017 at 10:37
4
\$\begingroup\$

Bash, 25 17 bytes

getconf LONG_BIT

Thanks to Dennis for golfing help.

\$\endgroup\$
0
4
\$\begingroup\$

C, 22 bytes

f(){return(int**)0+8;}

This is a pointer-size based answer that assumes a native binary. The 0 is cast to int** (address 0x0). Then we add 8 to 0, which, in C advances, the pointer by sizeof(int*)*8. 4 bytes * 8 bits = 32, 8 bytes * 8 bits = 64. So we get (int**)0x20 and 0x40 which are then implicitly cast as integers by returning them from an implicitly int-returning function.

C, stand-alone, 34 bytes

main(){printf("%d\n",(int**)0+8);} 

C, fun with Unicode, 30 code-points, 34 bytes(UTF-8)

main(){puts((int**)U" ㈳㐶"+1);}
\$\endgroup\$
2
  • \$\begingroup\$ I've been trying to understand how this works, but I'm clueless. Can you add an explaination? \$\endgroup\$
    – Maya
    Jun 22, 2017 at 16:36
  • \$\begingroup\$ @jbcreix clever... \$\endgroup\$
    – Maya
    Jun 23, 2017 at 18:03
3
\$\begingroup\$

Java, 50 bytes

int b(){return com.sun.jna.Native.POINTER_SIZE*8;}

\$\endgroup\$
4
  • \$\begingroup\$ Is that a library? If yes, you should mention it! I don't see that class available in the Oracle's JDK 8 though (I don't have my usual JDK 6 and 7 at my disposal, atm). \$\endgroup\$ Jun 19, 2017 at 23:01
  • 2
    \$\begingroup\$ This answer is invalid. It doesn't print. \$\endgroup\$
    – Philipp
    Jun 20, 2017 at 10:42
  • 7
    \$\begingroup\$ Quoting Dennis: > It also says that the usual code golf rules apply, and returning from a function is part of our defaults for I/O. \$\endgroup\$
    – asu
    Jun 20, 2017 at 13:02
  • \$\begingroup\$ Change it into a lamba function for less bytes: ()->com.sun.jna.Native.POINTER_SIZE*8 \$\endgroup\$
    – Ferrybig
    Jun 25, 2017 at 12:02
3
\$\begingroup\$

PHP, 29 bytes

<?=@php_uname(m)[-1]-4?32:64;

https://3v4l.org/Y6JXv

\$\endgroup\$
7
  • \$\begingroup\$ Ooh. I like this one. How does it work? \$\endgroup\$
    – tuskiomi
    Jun 20, 2017 at 12:09
  • 4
    \$\begingroup\$ php_uname('m') returns x86_64 on a 64 bit OS, otherwise something like i386. 4 being the 6th character (5th 0 indexed) of the string, '4' - 4 == 0 == false. And @ just suppresses warnings for unquoted strings, and uninitialised offsets. \$\endgroup\$
    – Petah
    Jun 20, 2017 at 12:27
  • 2
    \$\begingroup\$ This detects the architecture of PHP, not of the OS. I'm running 32-bit PHP on a 64-bit Windows, php_uname('m') returns 'i586'. \$\endgroup\$ Jun 21, 2017 at 3:58
  • \$\begingroup\$ @GrasDouble well I guess ymmv, I works for me with Windows NT USER-PC 10.0 build 15063 (Windows 10) AMD64. \$\endgroup\$
    – Petah
    Jun 21, 2017 at 9:13
  • 1
    \$\begingroup\$ @tuskiomi this will print 64 if there is an 8-bit operating system \$\endgroup\$
    – Bja
    Jun 21, 2017 at 16:33
3
\$\begingroup\$

Python 3, 77 84 71 59 bytes

-13 bytes, thanks to @JonathanAllan!
Down to 59 by @Clearer

from platform import*;print({'4':64,'6':32}[machine()[-1]])

Try it online!

My fist time code-golfing :)
Should output the correct version even when running 32Bit-Python on 64bit-OS.
Assuming platform.machine() gives i*86 or x86 for 32Bit-OS. I don't have one available to check this. Output is 0 when OS is not in 64/32Bit
Edit: Added print statement, so it got 7 bytes longer

\$\endgroup\$
6
  • \$\begingroup\$ Not sure if it's acceptable because it is possible to run a 32 bit OS on a 64 bit machine (or to have some machine called a foo86 that is 64 bit :p), but if it is acceptable then you can save 9 (edit ...13!) bytes with print((a==64)*a+32*(a==86)). \$\endgroup\$ Jun 20, 2017 at 14:03
  • \$\begingroup\$ from platform import*;print({'4':64,'6':32}[machine()[-1]]) would work too. \$\endgroup\$
    – Clearer
    Jun 21, 2017 at 10:40
  • \$\begingroup\$ @Clearer This would miss following constraint: Important: Print any other non-empty string of alphanumeric characters if it's neither 32 or 64 bit.. \$\endgroup\$
    – tOmAtE
    Jun 22, 2017 at 7:41
  • \$\begingroup\$ @tOmAtE if it's neither 32 nor 64 bit, it will throw an exception, which prints a non-empty string. \$\endgroup\$
    – Clearer
    Jun 22, 2017 at 8:04
  • 2
    \$\begingroup\$ Try architecture(), saves the dict: from platform import*;print(architecture()[0][:2]) -> 50 bytes \$\endgroup\$ Jun 23, 2017 at 13:19

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.