Project: libraw (libraw/libraw), language: c++
Vulnerability instance: libraw.cve-2023-1729
Sanitizer: address

================= Bug Report (1/2) ==================
## Source: GitHub Issue
## URL: https://github.com/LibRaw/LibRaw/issues/557
## Description:
Issue: LibRaw/LibRaw#557
Title: There exists heap-buffer-overflow when using function raw2image_ex(int)
State: closed
Created by: DaisyPo
Created at: 2023-01-14 02:34:12+00:00
Labels: waitforfeedback

Issue Body:
## Description
There exists heap-buffer-overflow in LibRaw::raw2image_ex(int) src/preprocessing/raw2image.cpp:492
## My test program
dcraw_half in  Libraw/bin
## Command and argument
./dcraw_half crash_dcraw_half  
## Crash Information
The output of exampletest with address sanitizer enabled
```
==611348==ERROR: AddressSanitizer: heap-buffer-overflow on address 0x62d000013300 at pc 0x7fc7701d804d bp 0x7ffc1d184d60 sp 0x7ffc1d184508
WRITE of size 2224 at 0x62d000013300 thread T0
    #0 0x7fc7701d804c in __interceptor_memmove ../../../../src/libsanitizer/sanitizer_common/sanitizer_common_interceptors.inc:773
    #1 0x7fc770001f0e in LibRaw::raw2image_ex(int) src/preprocessing/raw2image.cpp:492
    #2 0x7fc76ffd2bd3 in LibRaw::dcraw_process() src/postprocessing/dcraw_process.cpp:43
    #3 0x56227007b71b in main samples/dcraw_half.c:66
    #4 0x7fc76f814082 in __libc_start_main ../csu/libc-start.c:308
    #5 0x56227007be0d in _start (/root/target/latest/LibRaw-0.21.1/build_afl_asan/bin/dcraw_half+0x2e0d)

0x62d000013300 is located 0 bytes to the right of 36608-byte region [0x62d00000a400,0x62d000013300)
allocated by thread T0 here:
    #0 0x7fc770244a06 in __interceptor_calloc ../../../../src/libsanitizer/asan/asan_malloc_linux.cc:153
    #1 0x7fc77004cca5 in libraw_memmgr::calloc(unsigned long, unsigned long) libraw/libraw_alloc.h:56
    #2 0x7fc77004cca5 in LibRaw::calloc(unsigned long, unsigned long) src/utils/utils_libraw.cpp:271

SUMMARY: AddressSanitizer: heap-buffer-overflow ../../../../src/libsanitizer/sanitizer_common/sanitizer_common_interceptors.inc:773 in __interceptor_memmove
Shadow bytes around the buggy address:
  0x0c5a7fffa610: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
  0x0c5a7fffa620: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
  0x0c5a7fffa630: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
  0x0c5a7fffa640: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
  0x0c5a7fffa650: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
=>0x0c5a7fffa660:[fa]fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa
  0x0c5a7fffa670: fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa
  0x0c5a7fffa680: fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa
  0x0c5a7fffa690: fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa
  0x0c5a7fffa6a0: fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa
  0x0c5a7fffa6b0: fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa
Shadow byte legend (one shadow byte represents 8 application bytes):
  Addressable:           00
  Partially addressable: 01 02 03 04 05 06 07 
  Heap left redzone:       fa
  Freed heap region:       fd
  Stack left redzone:      f1
  Stack mid redzone:       f2
  Stack right redzone:     f3
  Stack after return:      f5
  Stack use after scope:   f8
  Global redzone:          f9
  Global init order:       f6
  Poisoned by user:        f7
  Container overflow:      fc
  Array cookie:            ac
  Intra object redzone:    bb
  ASan internal:           fe
  Left alloca redzone:     ca
  Right alloca redzone:    cb
  Shadow gap:              cc
==611348==ABORTING
```
## Version
LibRaw 0.21.1 release
the commit is cccb976
## POC File
[crash_dcraw_half.zip](https://github.com/LibRaw/LibRaw/files/10416372/crash_dcraw_half.zip)




Comments:
Comment by LibRaw on 2023-01-14 09:54:47+00:00:
LibRaw::open_file() refuses your sample as 'unsupported or not raw file'.

Please make sure you're submitted the correct POC file.

---

Comment by DaisyPo on 2023-01-14 10:16:34+00:00:
I've tried again and didn't see 'unsupported or not raw file'.  [crash_dcraw_half.zip](https://github.com/LibRaw/LibRaw/files/10416372/crash_dcraw_half.zip) needs to be extracted.  I also used the zip file to run the command just now, this will be "libraw  Unsupported file format or not RAW file".

---

Comment by LibRaw on 2023-01-14 10:35:47+00:00:
Sure, I know what zip files are.

The MD5 checksum for the file you provided is: c39ba6fb6d5ee34e2b0833af6acbebc6

It is refused by LibRaw 0.21.1

---

Comment by DaisyPo on 2023-01-14 10:45:42+00:00:
![image](https://user-images.githubusercontent.com/56296073/212468021-de243fff-c1ac-4998-8b6d-183cf8f627c7.png)
The direct result is in the picture above. It's "malloc(): corrupted top size".Does this mean LibRaw 0.21.1 refused the file? 

---

Comment by LibRaw on 2023-01-14 10:58:21+00:00:
Thank you for your screenshot.
Anyway, I'm unable to reproduce the problem using the POC file you provided.

---

Comment by DaisyPo on 2023-01-14 13:42:51+00:00:
My friend helped me compile LibRaw 0.21.1 in another server(also Linux os),and I use GDB to analyse the same POC file. It turns out  segmentation fault. A little different from the original result (SIGABRT), but still the same position raw2image.cpp:492. 
![image](https://user-images.githubusercontent.com/56296073/212474834-dc7dbb32-d4c6-4fda-b12a-f95e2cdb6186.png)

At present, I have no idea why you can't reproduce it. I really feel confused. 

---

Comment by LibRaw on 2023-01-14 13:53:41+00:00:
Sorry, no linux here, but the file is not refused by open_file() on FreeBSD and not crashed.

Investigating....


---

Comment by DaisyPo on 2023-01-14 13:58:13+00:00:
Sorry，I always test in Linux OS and forgot to tell you at the beginning. Maybe the bug only exists  in Linux? I'm not sure.
 

---

Comment by LibRaw on 2023-01-14 17:04:08+00:00:
This patch should fix the problem


---

Comment by DaisyPo on 2023-01-15 02:39:47+00:00:
The patch is 9ab70f6 , right? I've used the patch and it works well.

---

Comment by LibRaw on 2023-01-15 06:33:01+00:00:
Oh, sorry, forgot to provide patch link. Yes, it is https://github.com/LibRaw/LibRaw/commit/9ab70f6dca19229cb5caad7cc31af4e7501bac93

Closing as confirmed fixed.

---

Comment by kaviev on 2023-06-28 11:55:02+00:00:
Does this issue only affect Libraw version 0.21.1 ?

---

Comment by risicle on 2023-08-12 14:12:55+00:00:
Still no release with the fix?

Attachments:
https://github.com/LibRaw/LibRaw/files/10416372/crash_dcraw_half.zip

Commit References:
9ab70f6dca19229cb5caad7cc31af4e7501bac93

================= Bug Report (2/2) ==================
## Source: Red Hat Bugzilla
## URL: https://bugzilla.redhat.com/show_bug.cgi?id=2188240
## Description:
Bugzilla ID: 2188240
Title: CVE-2023-1729 LibRaw: a heap-buffer-overflow in raw2image_ex()

Description
Marian Rehak 2023-04-20 08:52:02 UTC
There exists heap-buffer-overflow when using function raw2image_ex(int).


Comments:
Comment 1
Marian Rehak 2023-04-20 10:52:07 UTC
Created LibRaw tracking bugs for this issue:

Affects: fedora-all [bug 2188274]


Created digikam tracking bugs for this issue:

Affects: epel-all [bug 2188276]
Affects: fedora-all [bug 2188275]


Created mingw-LibRaw tracking bugs for this issue:

Affects: fedora-all [bug 2188277]

---

Comment 3
Gwyn Ciesla 2023-04-20 15:12:06 UTC
I need access to 2175642 if I am to patch LibRaw for Fedora.

---

Comment 4
bugzilla_throwaway 2023-04-21 09:35:59 UTC
Hi, could you please provide more information on this CVE? Like a patch or the fixed version? Thanks!

---

Comment 5
Debarshi Ray 2023-04-27 13:47:02 UTC
(In reply to bugzilla_throwaway from comment #4)
> Hi, could you please provide more information on this CVE? Like a patch or
> the fixed version? Thanks!

Yeah, I can't fix this for RHEL without a reference to a patch or an issue.  I don't see any relevant commits in 2023 to the upstream 0.21-stable branch:
https://github.com/LibRaw/LibRaw/tree/0.21-stable

---

Comment 6
nucleo 2023-05-07 17:28:53 UTC
External reference to issue on https://access.redhat.com/security/cve/CVE-2023-1729 is https://github.com/LibRaw/LibRaw/issues/557
Should I apply fix https://github.com/LibRaw/LibRaw/commit/9ab70f6dca19229cb5caad7cc31af4e7501bac93 to digiKam?

Build script:
#!/bin/bash -eu
# Minimized build script with only core build commands
set -eu
autoreconf --install
./configure --disable-examples
make -j$(nproc)

Dockerfile:
FROM hwiwonlee/secb.base:latest
RUN apt-get update && apt-get install -y make autoconf automake libtool pkg-config zlib1g-dev
RUN git clone https://github.com/libraw/libraw libraw
RUN git -C libraw checkout 62f0423663f2fdfd46eedecd4690e39fa899d0a6
WORKDIR $SRC/libraw
COPY build.sh $SRC/

Additional files:
filename: libraw_fuzzer.cc
content: /*  Copyright 2020 Google Inc.

Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at

      http://www.apache.org/licenses/LICENSE-2.0

Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/

#include <stddef.h>
#include <stdint.h>

#include <string>
#include <fuzzer/FuzzedDataProvider.h>

#include <libraw.h>

enum InterpolationOptions {
  Linear = 0,
  Vng = 1, 
  Ppg = 2,
  Ahd = 3,
  Dcb = 4,
  Dht = 11,
  AhdModified = 12
};
static const InterpolationOptions options[] = {Linear, Vng, Ppg, Ahd, Dcb, Dht, AhdModified};

extern "C" int LLVMFuzzerTestOneInput(const uint8_t* data, size_t size) {
  // Input less than 15mb
  if (size > 15000000) {
    return 0;
  }

  FuzzedDataProvider fdp(data, size);
  LibRaw lib_raw;

  for(int i =0; i < 4; i++)
    lib_raw.output_params_ptr()->aber[i] = fdp.ConsumeFloatingPoint<double>();
  for(int i =0; i < 4; i++)
    lib_raw.output_params_ptr()->user_mul[i] = fdp.ConsumeFloatingPoint<float>();
  for(int i =0; i < 2; i++)
    lib_raw.output_params_ptr()->gamm[i] = fdp.ConsumeFloatingPoint<double>();
  lib_raw.output_params_ptr()->bright = fdp.ConsumeFloatingPoint<float>();
  lib_raw.output_params_ptr()->threshold = fdp.ConsumeFloatingPoint<float>();
  lib_raw.output_params_ptr()->use_auto_wb = fdp.ConsumeIntegral<int>();
  lib_raw.output_params_ptr()->output_color = fdp.ConsumeIntegralInRange<int>(0, 6);
  lib_raw.output_params_ptr()->user_flip = fdp.ConsumeIntegralInRange<int>(0, 7);
  lib_raw.output_params_ptr()->user_black = fdp.ConsumeIntegral<int>();
  lib_raw.output_params_ptr()->user_sat = fdp.ConsumeIntegral<int>();
  lib_raw.output_params_ptr()->auto_bright_thr = fdp.ConsumeFloatingPoint<float>();
  lib_raw.output_params_ptr()->adjust_maximum_thr = fdp.ConsumeFloatingPointInRange<float>(0.f, 1.f);
  lib_raw.output_params_ptr()->fbdd_noiserd = fdp.ConsumeIntegralInRange<int>(0, 5);

  std::vector<char> payload = fdp.ConsumeRemainingBytes<char>();
  int result = lib_raw.open_buffer(payload.data(), payload.size());
  if (result != LIBRAW_SUCCESS) {
    return 0;
  }

  result = lib_raw.unpack();
  if (result != LIBRAW_SUCCESS) {
    return 0;
  }

  result = lib_raw.unpack_thumb();
  if (result != LIBRAW_SUCCESS) {
    return 0;
  }

  result = lib_raw.raw2image();
  if (result != LIBRAW_SUCCESS) {
    return 0;
  }
  lib_raw.free_image();

  for (int i = 0; i < sizeof(options)/sizeof(*options); i++) {
    lib_raw.output_params_ptr()->user_qual = static_cast<int>(options[i]);

    result = lib_raw.dcraw_process();
    if (result != LIBRAW_SUCCESS) {
      return 0;
    }
  }

  return 0;
}