diff --git a/library/data/buffer.lean b/library/data/buffer.lean deleted file mode 100644 index 17d18d317c..0000000000 --- a/library/data/buffer.lean +++ /dev/null @@ -1,147 +0,0 @@ -/- -Copyright (c) 2017 Microsoft Corporation. All rights reserved. -Released under Apache 2.0 license as described in the file LICENSE. -Authors: Leonardo de Moura --/ -universes u w - -def buffer (α : Type u) := Σ n, array n α - -def mk_buffer {α : Type u} : buffer α := -⟨0, {data := λ i, fin.elim0 i}⟩ - -def array.to_buffer {α : Type u} {n : nat} (a : array n α) : buffer α := -⟨n, a⟩ - -namespace buffer -variables {α : Type u} {β : Type w} - -def nil : buffer α := -mk_buffer - -def size (b : buffer α) : nat := -b.1 - -def to_array (b : buffer α) : array (b.size) α := -b.2 - -def push_back : buffer α → α → buffer α -| ⟨n, a⟩ v := ⟨n+1, a.push_back v⟩ - -def pop_back : buffer α → buffer α -| ⟨0, a⟩ := ⟨0, a⟩ -| ⟨n+1, a⟩ := ⟨n, a.pop_back⟩ - -def read : Π (b : buffer α), fin b.size → α -| ⟨n, a⟩ i := a.read i - -def write : Π (b : buffer α), fin b.size → α → buffer α -| ⟨n, a⟩ i v := ⟨n, a.write i v⟩ - -def read' [inhabited α] : buffer α → nat → α -| ⟨n, a⟩ i := a.read' i - -def write' : buffer α → nat → α → buffer α -| ⟨n, a⟩ i v := ⟨n, a.write' i v⟩ - -lemma read_eq_read' [inhabited α] (b : buffer α) (i : nat) (h : i < b.size) : read b ⟨i, h⟩ = read' b i := -by cases b; unfold read read'; simp [array.read_eq_read'] - -lemma write_eq_write' (b : buffer α) (i : nat) (h : i < b.size) (v : α) : write b ⟨i, h⟩ v = write' b i v := -by cases b; unfold write write'; simp [array.write_eq_write'] - -def to_list (b : buffer α) : list α := -b.to_array.to_list - -protected def to_string (b : buffer char) : string := -b.to_array.to_list.as_string - -def append_list {α : Type u} : buffer α → list α → buffer α -| b [] := b -| b (v::vs) := append_list (b.push_back v) vs - -def append_string (b : buffer char) (s : string) : buffer char := -b.append_list s.to_list - -lemma lt_aux_1 {a b c : nat} (h : a + c < b) : a < b := -nat.lt_of_le_of_lt (nat.le_add_right a c) h - -lemma lt_aux_2 {n} (h : n > 0) : n - 1 < n := -have h₁ : 1 > 0, from dec_trivial, -nat.sub_lt h h₁ - -lemma lt_aux_3 {n i} (h : i + 1 < n) : n - 2 - i < n := -have n > 0, from nat.lt_trans (nat.zero_lt_succ i) h, -have n - 2 < n, from nat.sub_lt this (dec_trivial), -nat.lt_of_le_of_lt (nat.sub_le _ _) this - -def append_array {α : Type u} {n : nat} (nz : n > 0) : buffer α → array n α → ∀ i : nat, i < n → buffer α -| ⟨m, b⟩ a 0 _ := - let i : fin n := ⟨n - 1, lt_aux_2 nz⟩ in - ⟨m+1, b.push_back (a.read i)⟩ -| ⟨m, b⟩ a (j+1) h := - let i : fin n := ⟨n - 2 - j, lt_aux_3 h⟩ in - append_array ⟨m+1, b.push_back (a.read i)⟩ a j (lt_aux_1 h) - -protected def append {α : Type u} : buffer α → buffer α → buffer α -| b ⟨0, a⟩ := b -| b ⟨n+1, a⟩ := append_array (nat.zero_lt_succ _) b a n (nat.lt_succ_self _) - -def iterate : Π b : buffer α, β → (fin b.size → α → β → β) → β -| ⟨_, a⟩ b f := a.iterate b f - -def foreach : Π b : buffer α, (fin b.size → α → α) → buffer α -| ⟨n, a⟩ f := ⟨n, a.foreach f⟩ - -def map (f : α → α) : buffer α → buffer α -| ⟨n, a⟩ := ⟨n, a.map f⟩ - -def foldl : buffer α → β → (α → β → β) → β -| ⟨_, a⟩ b f := a.foldl b f - -def rev_iterate : Π (b : buffer α), β → (fin b.size → α → β → β) → β -| ⟨_, a⟩ b f := a.rev_iterate b f - -/- -def take (b : buffer α) (n : nat) : buffer α := -if h : n ≤ b.size then ⟨n, b.to_array.take n h⟩ else b - -def take_right (b : buffer α) (n : nat) : buffer α := -if h : n ≤ b.size then ⟨n, b.to_array.take_right n h⟩ else b - -def drop (b : buffer α) (n : nat) : buffer α := -if h : n ≤ b.size then ⟨_, b.to_array.drop n h⟩ else b - -def reverse (b : buffer α) : buffer α := -⟨b.size, b.to_array.reverse⟩ --/ - -protected def mem (v : α) (a : buffer α) : Prop := ∃i, read a i = v - -instance : has_mem α (buffer α) := ⟨buffer.mem⟩ - -instance : has_append (buffer α) := -⟨buffer.append⟩ - -instance [has_repr α] : has_repr (buffer α) := -⟨repr ∘ to_list⟩ - -meta instance [has_to_format α] : has_to_format (buffer α) := -⟨to_fmt ∘ to_list⟩ - -meta instance [has_to_tactic_format α] : has_to_tactic_format (buffer α) := -⟨tactic.pp ∘ to_list⟩ - -end buffer - -def list.to_buffer {α : Type u} (l : list α) : buffer α := -mk_buffer.append_list l - -@[reducible] def char_buffer := buffer char - -/-- Convert a format object into a character buffer with the provided - formatting options. -/ -meta constant format.to_buffer : format → options → buffer char - -def string.to_char_buffer (s : string) : char_buffer := -buffer.nil.append_string s diff --git a/library/system/io.lean b/library/system/io.lean index 825a8b075f..929fe49f2a 100644 --- a/library/system/io.lean +++ b/library/system/io.lean @@ -115,31 +115,31 @@ monad_io_file_system.flush def close : handle → io unit := monad_io_file_system.close -def read : handle → nat → io char_buffer := +def read : handle → nat → io string := monad_io_file_system.read -def write : handle → char_buffer → io unit := +def write : handle → string → io unit := monad_io_file_system.write def get_char (h : handle) : io char := do b ← read h 1, - if h : b.size = 1 then return $ b.read ⟨0, h.symm ▸ nat.zero_lt_one⟩ - else io.fail "get_char failed" + if b.is_empty then io.fail "get_char failed" + else return b.mk_iterator.curr -def get_line : handle → io char_buffer := +def get_line : handle → io string := monad_io_file_system.get_line def put_char (h : handle) (c : char) : io unit := -write h (mk_buffer.push_back c) +write h (to_string c) def put_str (h : handle) (s : string) : io unit := -write h (mk_buffer.append_string s) +write h s def put_str_ln (h : handle) (s : string) : io unit := put_str h s >> put_str h "\n" -def read_to_end (h : handle) : io char_buffer := -iterate mk_buffer $ λ r, +def read_to_end (h : handle) : io string := +iterate "" $ λ r, do done ← is_eof h, if done then return none @@ -147,7 +147,7 @@ iterate mk_buffer $ λ r, c ← read h 1024, return $ some (r ++ c) -def read_file (s : string) (bin := ff) : io char_buffer := +def read_file (s : string) (bin := ff) : io string := do h ← mk_file_handle s io.mode.read bin, read_to_end h @@ -199,11 +199,11 @@ format.print (to_fmt a) read into `string` which is then returned. -/ def io.cmd (args : io.process.spawn_args) : io string := do child ← io.proc.spawn { stdout := io.process.stdio.piped, ..args }, - buf ← io.fs.read_to_end child.stdout, + s ← io.fs.read_to_end child.stdout, io.fs.close child.stdout, exitv ← io.proc.wait child, when (exitv ≠ 0) $ io.fail $ "process exited with status " ++ repr exitv, - return buf.to_string + return s /-- This is the "back door" into the `io` monad, allowing IO computation to be performed during tactic execution. diff --git a/library/system/io_interface.lean b/library/system/io_interface.lean index 4b38c573b6..a2fd60edd7 100644 --- a/library/system/io_interface.lean +++ b/library/system/io_interface.lean @@ -3,7 +3,7 @@ Copyright (c) 2018 Microsoft Corporation. All rights reserved. Released under Apache 2.0 license as described in the file LICENSE. Authors: Leonardo de Moura -/ -import data.buffer system.random +import system.random inductive io.error | other : string → io.error @@ -55,9 +55,9 @@ class monad_io_file_system (m : Type → Type → Type) [monad_io m] := (is_eof : (handle m) → m io.error bool) (flush : (handle m) → m io.error unit) (close : (handle m) → m io.error unit) -(read : (handle m) → nat → m io.error char_buffer) -(write : (handle m) → char_buffer → m io.error unit) -(get_line : (handle m) → m io.error char_buffer) +(read : (handle m) → nat → m io.error string) +(write : (handle m) → string → m io.error unit) +(get_line : (handle m) → m io.error string) (stdin : m io.error (handle m)) (stdout : m io.error (handle m)) (stderr : m io.error (handle m)) diff --git a/src/library/handle.cpp b/src/library/handle.cpp index 6026568d16..d9d6d12d32 100644 --- a/src/library/handle.cpp +++ b/src/library/handle.cpp @@ -28,7 +28,7 @@ Author: Leonardo de Moura & Jared Roesch namespace lean { -void handle::write(buffer & buf) { +void handle::write(std::string const & buf) { auto sz = buf.size(); if (fwrite(buf.data(), 1, sz, m_file) != sz) { std::cout << "write_error: " << errno << std::endl; diff --git a/src/library/handle.h b/src/library/handle.h index aa1698af37..b56e44a32e 100644 --- a/src/library/handle.h +++ b/src/library/handle.h @@ -27,7 +27,7 @@ public: ~handle(); - void write(buffer & data); + void write(std::string const & data); void flush(); bool is_stdin(); diff --git a/src/library/vm/vm_io.cpp b/src/library/vm/vm_io.cpp index 250433e6a0..de4c9e5e88 100644 --- a/src/library/vm/vm_io.cpp +++ b/src/library/vm/vm_io.cpp @@ -185,26 +185,18 @@ static vm_obj fs_close(vm_obj const & h, vm_obj const &) { } } -static vm_obj mk_buffer(parray const & a) { - return mk_vm_pair(mk_vm_nat(a.size()), to_obj(a)); -} - static vm_obj fs_read(vm_obj const & h, vm_obj const & n, vm_obj const &) { handle_ref const & href = to_handle(h); if (href->is_closed()) return mk_handle_has_been_closed_error(); buffer tmp; unsigned num = force_to_unsigned(n); /* TODO(Leo): handle size_t */ tmp.resize(num, 0); - size_t sz = fread(tmp.data(), 1, num, href->m_file); + fread(tmp.data(), 1, num, href->m_file); if (ferror(href->m_file)) { clearerr(href->m_file); return mk_io_failure("read failed"); } - parray r; - for (size_t i = 0; i < sz; i++) { - r.push_back(mk_vm_simple(static_cast(tmp[i]))); - } - return mk_io_result(mk_buffer(r)); + return mk_io_result(to_obj(std::string(tmp.data()))); } static vm_obj fs_write(vm_obj const & h, vm_obj const & b, vm_obj const &) { @@ -214,15 +206,8 @@ static vm_obj fs_write(vm_obj const & h, vm_obj const & b, vm_obj const &) { return mk_handle_has_been_closed_error(); } - buffer tmp; - parray const & a = to_array(cfield(b, 1)); - unsigned sz = a.size(); - for (unsigned i = 0; i < sz; i++) { - tmp.push_back(static_cast(cidx(a[i]))); - } - try { - href->write(tmp); + href->write(to_string(b)); return mk_io_result(mk_vm_unit()); } catch (handle_exception e) { return mk_io_failure("write failed"); @@ -236,7 +221,7 @@ static vm_obj fs_get_line(vm_obj const & h, vm_obj const &) { return mk_handle_has_been_closed_error(); } - parray r; + std::string r; while (true) { int c = fgetc(href->m_file); if (ferror(href->m_file)) { @@ -245,11 +230,11 @@ static vm_obj fs_get_line(vm_obj const & h, vm_obj const &) { } if (c == EOF) break; - r.push_back(mk_vm_simple(static_cast(static_cast(c)))); + r.push_back(static_cast(c)); if (c == '\n') break; } - return mk_io_result(mk_buffer(r)); + return mk_io_result(to_obj(r)); } static vm_obj fs_stdin(vm_obj const &) {