Coverage for /pythoncovmergedfiles/medio/medio/src/dulwich/fuzzing/fuzz-targets/fuzz_repo.py: 52%

Shortcuts on this page

r m x   toggle line displays

j k   next/prev highlighted chunk

0   (zero) top of page

1   (one) first highlighted chunk

44 statements  

1###### Coverage stub 

2import atexit 

3import coverage 

4cov = coverage.coverage(data_file='.coverage', cover_pylib=True) 

5cov.start() 

6# Register an exist handler that will print coverage 

7def exit_handler(): 

8 cov.stop() 

9 cov.save() 

10atexit.register(exit_handler) 

11####### End of coverage stub 

12# SPDX-License-Identifier: Apache-2.0 OR GPL-2.0-or-later 

13 

14import os 

15import sys 

16import tempfile 

17from typing import Optional 

18 

19import atheris 

20 

21with atheris.instrument_imports(): 

22 # We instrument `test_utils` as well, so it doesn't block coverage analysis in Fuzz Introspector: 

23 from test_utils import EnhancedFuzzedDataProvider, is_expected_exception 

24 

25 from dulwich.repo import ( 

26 InvalidUserIdentity, 

27 Repo, 

28 ) 

29 

30 

31def TestOneInput(data) -> Optional[int]: 

32 fdp = EnhancedFuzzedDataProvider(data) 

33 with tempfile.TemporaryDirectory() as temp_dir: 

34 repo = Repo.init(temp_dir) 

35 repo.set_description(fdp.ConsumeRandomBytes()) 

36 repo.get_description() 

37 

38 try: 

39 # Generate a minimal set of files based on fuzz data to minimize I/O operations. 

40 file_names = [ 

41 f"File{i}{fdp.ConsumeRandomString(without_surrogates=True)}" 

42 for i in range(min(3, fdp.ConsumeIntInRange(1, 3))) 

43 ] 

44 for file in file_names: 

45 with open(os.path.join(temp_dir, file), "wb") as f: 

46 f.write(fdp.ConsumeRandomBytes()) 

47 except (ValueError, OSError): 

48 # Exit early if the fuzzer generates an invalid filename. 

49 return -1 

50 

51 try: 

52 repo.stage(file_names) 

53 repo.do_commit( 

54 message=fdp.ConsumeRandomBytes(), 

55 committer=fdp.ConsumeRandomBytes(), 

56 author=fdp.ConsumeRandomBytes(), 

57 commit_timestamp=fdp.ConsumeRandomInt(), 

58 commit_timezone=fdp.ConsumeRandomInt(), 

59 author_timestamp=fdp.ConsumeRandomInt(), 

60 author_timezone=fdp.ConsumeRandomInt(), 

61 ) 

62 except InvalidUserIdentity: 

63 return -1 

64 except ValueError as e: 

65 if is_expected_exception(["Unable to handle non-minute offset"], e): 

66 return -1 

67 else: 

68 raise e 

69 

70 

71def main() -> None: 

72 atheris.Setup(sys.argv, TestOneInput) 

73 atheris.Fuzz() 

74 

75 

76if __name__ == "__main__": 

77 main()