extern void getenv_(char *fname, char *value, int flen, int vlen) {
  extern char **_environ;
  register char **env = _environ;
  register char *ep, *fp, *flast;
  flast = fname + flen;
  for (fp = fname; fp < flast; ++fp)
    if (*fp == ' ') {
      flast = fp;
      break;
    }
  while (ep = *env++) {
    for (fp = fname; fp < flast;)
      if (*fp++ != *ep++)
        goto endloop;
    if (*ep++ == '=') {
      while (*ep && --vlen >= 0)
        *value++ = *ep++;
      goto blank;
    }
  endloop:;
  }
blank:
  while (--vlen >= 0)
    *value++ = ' ';
  return;
}


x86 assembly (clang, -O0):
<getenv_>:
push   %rbp
mov    %rsp,%rbp
mov    %rdi,-0x8(%rbp)
mov    %rsi,-0x10(%rbp)
mov    %edx,-0x14(%rbp)
mov    %ecx,-0x18(%rbp)
mov    0x2ec7(%rip),%rax
mov    (%rax),%rax
mov    %rax,-0x20(%rbp)
mov    -0x8(%rbp),%rax
movslq -0x14(%rbp),%rcx
add    %rcx,%rax
mov    %rax,-0x38(%rbp)
mov    -0x8(%rbp),%rax
mov    %rax,-0x30(%rbp)
mov    -0x30(%rbp),%rax
cmp    -0x38(%rbp),%rax
jae    1178 <getenv_+0x78>
mov    -0x30(%rbp),%rax
movsbl (%rax),%eax
cmp    $0x20,%eax
jne    1162 <getenv_+0x62>
mov    -0x30(%rbp),%rax
mov    %rax,-0x38(%rbp)
jmp    1178 <getenv_+0x78>
jmp    1167 <getenv_+0x67>
mov    -0x30(%rbp),%rax
add    $0x1,%rax
mov    %rax,-0x30(%rbp)
jmp    1137 <getenv_+0x37>
jmp    117d <getenv_+0x7d>
mov    -0x20(%rbp),%rax
mov    %rax,%rcx
add    $0x8,%rcx
mov    %rcx,-0x20(%rbp)
mov    (%rax),%rax
mov    %rax,-0x28(%rbp)
cmp    $0x0,%rax
je     1276 <getenv_+0x176>
mov    -0x8(%rbp),%rax
mov    %rax,-0x30(%rbp)
mov    -0x30(%rbp),%rax
cmp    -0x38(%rbp),%rax
jae    11e9 <getenv_+0xe9>
mov    -0x30(%rbp),%rax
mov    %rax,%rcx
add    $0x1,%rcx
mov    %rcx,-0x30(%rbp)
movsbl (%rax),%eax
mov    -0x28(%rbp),%rcx
mov    %rcx,%rdx
add    $0x1,%rdx
mov    %rdx,-0x28(%rbp)
movsbl (%rcx),%ecx
cmp    %ecx,%eax
je     11e4 <getenv_+0xe4>
jmp    1271 <getenv_+0x171>
jmp    11a5 <getenv_+0xa5>
mov    -0x28(%rbp),%rax
mov    %rax,%rcx
add    $0x1,%rcx
mov    %rcx,-0x28(%rbp)
movsbl (%rax),%eax
cmp    $0x3d,%eax
jne    126c <getenv_+0x16c>
jmp    1209 <getenv_+0x109>
mov    -0x28(%rbp),%rax
movsbl (%rax),%ecx
xor    %eax,%eax
cmp    $0x0,%ecx
mov    %al,-0x39(%rbp)
je     1230 <getenv_+0x130>
mov    -0x18(%rbp),%eax
add    $0xffffffff,%eax
mov    %eax,-0x18(%rbp)
cmp    $0x0,%eax
setge  %al
mov    %al,-0x39(%rbp)
mov    -0x39(%rbp),%al
test   $0x1,%al
jne    1240 <getenv_+0x140>
jmp    1267 <getenv_+0x167>
mov    -0x28(%rbp),%rax
mov    %rax,%rcx
add    $0x1,%rcx
mov    %rcx,-0x28(%rbp)
mov    (%rax),%cl
mov    -0x10(%rbp),%rax
mov    %rax,%rdx
add    $0x1,%rdx
mov    %rdx,-0x10(%rbp)
mov    %cl,(%rax)
jmp    1209 <getenv_+0x109>
jmp    127b <getenv_+0x17b>
jmp    1271 <getenv_+0x171>
jmp    117d <getenv_+0x7d>
jmp    127b <getenv_+0x17b>
jmp    1280 <getenv_+0x180>
mov    -0x18(%rbp),%eax
add    $0xffffffff,%eax
mov    %eax,-0x18(%rbp)
cmp    $0x0,%eax
jl     12a9 <getenv_+0x1a9>
mov    -0x10(%rbp),%rax
mov    %rax,%rcx
add    $0x1,%rcx
mov    %rcx,-0x10(%rbp)
movb   $0x20,(%rax)
jmp    1280 <getenv_+0x180>
pop    %rbp
ret

x86 assembly (clang, -O2):
<getenv_>:
push   %rax
mov    0x2ec8(%rip),%rax
mov    (%rax),%r8
movslq %edx,%rax
lea    (%rdi,%rax,1),%r9
test   %eax,%eax
jle    1157 <getenv_+0x47>
mov    %rdi,%rax
nopl   0x0(%rax)
cmpb   $0x20,(%rax)
je     1140 <getenv_+0x30>
add    $0x1,%rax
cmp    %r9,%rax
jb     1130 <getenv_+0x20>
jmp    1157 <getenv_+0x47>
mov    %rax,%r9
jmp    1157 <getenv_+0x47>
cs nopw 0x0(%rax,%rax,1)
nop
cmpb   $0x3d,-0x1(%r10)
je     118c <getenv_+0x7c>
mov    (%r8),%r10
test   %r10,%r10
je     11cb <getenv_+0xbb>
add    $0x8,%r8
add    $0x1,%r10
mov    %rdi,%rdx
nopw   0x0(%rax,%rax,1)
cmp    %r9,%rdx
jae    1150 <getenv_+0x40>
movzbl (%rdx),%r11d
add    $0x1,%rdx
lea    0x1(%r10),%rax
cmp    -0x1(%r10),%r11b
mov    %rax,%r10
je     1170 <getenv_+0x60>
jmp    1157 <getenv_+0x47>
mov    (%r10),%dl
test   %dl,%dl
je     11cb <getenv_+0xbb>
xor    %edi,%edi
test   %ecx,%ecx
mov    $0x0,%r8d
cmovs  %ecx,%r8d
add    $0xffffffff,%r8d
cs nopw 0x0(%rax,%rax,1)
nop
test   %ecx,%ecx
jle    11e5 <getenv_+0xd5>
mov    %dl,(%rsi,%rdi,1)
movzbl 0x1(%r10,%rdi,1),%edx
add    $0x1,%rdi
add    $0xffffffff,%ecx
test   %dl,%dl
jne    11b0 <getenv_+0xa0>
add    %rdi,%rsi
mov    %ecx,%r8d
test   %r8d,%r8d
jle    11e3 <getenv_+0xd3>
mov    %r8d,%edx
mov    %rsi,%rdi
mov    $0x20,%esi
call   1030 <memset@plt>
pop    %rax
ret
add    %rdi,%rsi
test   %r8d,%r8d
jg     11d3 <getenv_+0xc3>
jmp    11e3 <getenv_+0xd3>

LLVM IR (-O0):
@_environ = external global i8**
define void @getenv_(i8* %0, i8* %1, i32 %2, i32 %3) {
%5 = alloca i8*
%6 = alloca i8*
%7 = alloca i32
%8 = alloca i32
%9 = alloca i8**
%10 = alloca i8*
%11 = alloca i8*
%12 = alloca i8*
store i8* %0, i8** %5
store i8* %1, i8** %6
store i32 %2, i32* %7
store i32 %3, i32* %8
%13 = load i8**, i8*** @_environ
store i8** %13, i8*** %9
%14 = load i8*, i8** %5
%15 = load i32, i32* %7
%16 = sext i32 %15 to i64
%17 = getelementptr inbounds i8, i8* %14, i64 %16
store i8* %17, i8** %12
%18 = load i8*, i8** %5
store i8* %18, i8** %11
br label %19
19: ; preds = %31, %4
%20 = load i8*, i8** %11
%21 = load i8*, i8** %12
%22 = icmp ult i8* %20, %21
br i1 %22, label %23, label %34
23: ; preds = %19
%24 = load i8*, i8** %11
%25 = load i8, i8* %24
%26 = sext i8 %25 to i32
%27 = icmp eq i32 %26, 32
br i1 %27, label %28, label %30
28: ; preds = %23
%29 = load i8*, i8** %11
store i8* %29, i8** %12
br label %34
30: ; preds = %23
br label %31
31: ; preds = %30
%32 = load i8*, i8** %11
%33 = getelementptr inbounds i8, i8* %32, i32 1
store i8* %33, i8** %11
br label %19
34: ; preds = %28, %19
br label %35
35: ; preds = %84, %34
%36 = load i8**, i8*** %9
%37 = getelementptr inbounds i8*, i8** %36, i32 1
store i8** %37, i8*** %9
%38 = load i8*, i8** %36
store i8* %38, i8** %10
%39 = icmp ne i8* %38, null
br i1 %39, label %40, label %85
40: ; preds = %35
%41 = load i8*, i8** %5
store i8* %41, i8** %11
br label %42
42: ; preds = %57, %40
%43 = load i8*, i8** %11
%44 = load i8*, i8** %12
%45 = icmp ult i8* %43, %44
br i1 %45, label %46, label %58
46: ; preds = %42
%47 = load i8*, i8** %11
%48 = getelementptr inbounds i8, i8* %47, i32 1
store i8* %48, i8** %11
%49 = load i8, i8* %47
%50 = sext i8 %49 to i32
%51 = load i8*, i8** %10
%52 = getelementptr inbounds i8, i8* %51, i32 1
store i8* %52, i8** %10
%53 = load i8, i8* %51
%54 = sext i8 %53 to i32
%55 = icmp ne i32 %50, %54
br i1 %55, label %56, label %57
56: ; preds = %46
br label %84
57: ; preds = %46
br label %42
58: ; preds = %42
%59 = load i8*, i8** %10
%60 = getelementptr inbounds i8, i8* %59, i32 1
store i8* %60, i8** %10
%61 = load i8, i8* %59
%62 = sext i8 %61 to i32
%63 = icmp eq i32 %62, 61
br i1 %63, label %64, label %83
64: ; preds = %58
br label %65
65: ; preds = %76, %64
%66 = load i8*, i8** %10
%67 = load i8, i8* %66
%68 = sext i8 %67 to i32
%69 = icmp ne i32 %68, 0
br i1 %69, label %70, label %74
70: ; preds = %65
%71 = load i32, i32* %8
%72 = add nsw i32 %71, -1
store i32 %72, i32* %8
%73 = icmp sge i32 %72, 0
br label %74
74: ; preds = %70, %65
%75 = phi i1 [ false, %65 ], [ %73, %70 ]
br i1 %75, label %76, label %82
76: ; preds = %74
%77 = load i8*, i8** %10
%78 = getelementptr inbounds i8, i8* %77, i32 1
store i8* %78, i8** %10
%79 = load i8, i8* %77
%80 = load i8*, i8** %6
%81 = getelementptr inbounds i8, i8* %80, i32 1
store i8* %81, i8** %6
store i8 %79, i8* %80
br label %65
82: ; preds = %74
br label %86
83: ; preds = %58
br label %84
84: ; preds = %83, %56
br label %35
85: ; preds = %35
br label %86
86: ; preds = %85, %82
br label %87
87: ; preds = %91, %86
%88 = load i32, i32* %8
%89 = add nsw i32 %88, -1
store i32 %89, i32* %8
%90 = icmp sge i32 %89, 0
br i1 %90, label %91, label %94
91: ; preds = %87
%92 = load i8*, i8** %6
%93 = getelementptr inbounds i8, i8* %92, i32 1
store i8* %93, i8** %6
store i8 32, i8* %92
br label %87
94: ; preds = %87
ret void
}

LLVM IR (-O2):
@_environ = external global i8**
define void @getenv_(i8* %0, i8* nocapture writeonly %1, i32 %2, i32 %3) {
%5 = load i8**, i8*** @_environ
%6 = sext i32 %2 to i64
%7 = getelementptr inbounds i8, i8* %0, i64 %6
%8 = icmp sgt i32 %2, 0
br i1 %8, label %9, label %16
9: ; preds = %4, %13
%10 = phi i8* [ %14, %13 ], [ %0, %4 ]
%11 = load i8, i8* %10
%12 = icmp eq i8 %11, 32
br i1 %12, label %16, label %13
13: ; preds = %9
%14 = getelementptr inbounds i8, i8* %10, i64 1
%15 = icmp ult i8* %14, %7
br i1 %15, label %9, label %16
16: ; preds = %13, %9, %4
%17 = phi i8* [ %7, %4 ], [ %10, %9 ], [ %7, %13 ]
%18 = load i8*, i8** %5
%19 = icmp eq i8* %18, null
br i1 %19, label %59, label %20
20: ; preds = %16, %56
%21 = phi i8* [ %57, %56 ], [ %18, %16 ]
%22 = phi i8** [ %23, %56 ], [ %5, %16 ]
%23 = getelementptr inbounds i8*, i8** %22, i64 1
br label %24
24: ; preds = %20, %28
%25 = phi i8* [ %31, %28 ], [ %21, %20 ]
%26 = phi i8* [ %29, %28 ], [ %0, %20 ]
%27 = icmp ult i8* %26, %17
br i1 %27, label %28, label %34
28: ; preds = %24
%29 = getelementptr inbounds i8, i8* %26, i64 1
%30 = load i8, i8* %26
%31 = getelementptr inbounds i8, i8* %25, i64 1
%32 = load i8, i8* %25
%33 = icmp eq i8 %30, %32
br i1 %33, label %24, label %56
34: ; preds = %24
%35 = load i8, i8* %25
%36 = icmp eq i8 %35, 61
br i1 %36, label %37, label %56
37: ; preds = %34
%38 = getelementptr inbounds i8, i8* %25, i64 1
%39 = load i8, i8* %38
%40 = icmp eq i8 %39, 0
br i1 %40, label %59, label %41
41: ; preds = %37
%42 = call i32 @llvm.smin.i32(i32 %3, i32 0)
%43 = add i32 %42, -1
br label %44
44: ; preds = %41, %51
%45 = phi i8 [ %54, %51 ], [ %39, %41 ]
%46 = phi i8* [ %53, %51 ], [ %38, %41 ]
%47 = phi i32 [ %49, %51 ], [ %3, %41 ]
%48 = phi i8* [ %52, %51 ], [ %1, %41 ]
%49 = add nsw i32 %47, -1
%50 = icmp sgt i32 %47, 0
br i1 %50, label %51, label %59
51: ; preds = %44
%52 = getelementptr inbounds i8, i8* %48, i64 1
store i8 %45, i8* %48
%53 = getelementptr inbounds i8, i8* %46, i64 1
%54 = load i8, i8* %53
%55 = icmp eq i8 %54, 0
br i1 %55, label %59, label %44
56: ; preds = %28, %34
%57 = load i8*, i8** %23
%58 = icmp eq i8* %57, null
br i1 %58, label %59, label %20
59: ; preds = %56, %51, %44, %16, %37
%60 = phi i8* [ %1, %37 ], [ %1, %16 ], [ %52, %51 ], [ %48, %44 ], [ %1, %56 ]
%61 = phi i32 [ %3, %37 ], [ %3, %16 ], [ %49, %51 ], [ %43, %44 ], [ %3, %56 ]
%62 = icmp sgt i32 %61, 0
br i1 %62, label %63, label %65
63: ; preds = %59
%64 = zext i32 %61 to i64
br label %65
65: ; preds = %63, %59
ret void
}