summaryrefslogtreecommitdiff
path: root/test/Moretest/io.ml
blob: 395d035e9fad063546ed5062201def815de490f1 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
(* Test a file copy function *)

let test msg funct f1 f2 =
  print_string msg; print_newline();
  funct f1 f2;
  if Sys.command ("cmp " ^ f1 ^ " " ^ f2) = 0
  then print_string "passed"
  else print_string "FAILED";
  print_newline()

(* File copy with constant-sized chunks *)

let copy_file sz infile ofile =
  let ic = open_in infile in
  let oc = open_out ofile in
  let buffer = String.create sz in
  let rec copy () =
    let n = input ic buffer 0 sz in
    if n = 0 then () else begin
      output oc buffer 0 n;
      copy ()
    end in
  copy();
  close_in ic;
  close_out oc

(* File copy with random-sized chunks *)

let copy_random sz infile ofile =
  let ic = open_in infile in
  let oc = open_out ofile in
  let buffer = String.create sz in
  let rec copy () =
    let s = 1 + Random.int sz in
    let n = input ic buffer 0 s in
    if n = 0 then () else begin
      output oc buffer 0 n;
      copy ()
    end in
  copy();
  close_in ic;
  close_out oc

(* File copy line per line *)

let copy_line infile ofile =
  let ic = open_in infile in
  let oc = open_out ofile in
  try
    while true do
      output_string oc (input_line ic); output_char oc '\n'
    done
  with End_of_file ->
    close_in ic;
    close_out oc

(* Backward copy, with lots of seeks *)

let copy_seek chunksize infile ofile =
  let ic = open_in_bin infile in
  let oc = open_out_bin ofile in
  let size = in_channel_length ic in
  let buffer = String.create chunksize in
  for i = (size - 1) / chunksize downto 0 do
    seek_in ic (i * chunksize);
    seek_out oc (i * chunksize);
    let n = input ic buffer 0 chunksize in
    output oc buffer 0 n
  done;
  close_in ic;
  close_out oc

(* Create long lines of text *)

let make_lines ofile =
  let oc = open_out ofile in
  for i = 1 to 256 do
    output_string oc (String.make (i*64) '.'); output_char oc '\n'
  done;
  close_out oc

(* The test *)

let _ =
  test "16-byte chunks" (copy_file 16) "/vmunix" "/tmp/testio";
  test "256-byte chunks" (copy_file 256) "/vmunix" "/tmp/testio";
  test "4096-byte chunks" (copy_file 4096) "/vmunix" "/tmp/testio";
  test "65536-byte chunks" (copy_file 65536) "/vmunix" "/tmp/testio";
  test "19-byte chunks" (copy_file 19) "/vmunix" "/tmp/testio";
  test "263-byte chunks" (copy_file 263) "/vmunix" "/tmp/testio";
  test "4011-byte chunks" (copy_file 4011) "/vmunix" "/tmp/testio";
  test "0...8192 byte chunks" (copy_random 8192) "/vmunix" "/tmp/testio";
  test "line per line, short lines" copy_line "/etc/hosts" "/tmp/testio";
  make_lines "/tmp/lines";
  test "line per line, short and long lines" copy_line "/tmp/lines" "/tmp/testio";
  test "backwards, 4096-byte chunks" (copy_seek 4096) "/vmunix" "/tmp/testio"; 
  test "backwards, 64-byte chunks" (copy_seek 64) "/vmunix" "/tmp/testio"; 
  Sys.remove "/tmp/lines";
  Sys.remove "/tmp/testio";
  exit 0