~rbn/neinp

ref: 280ca11dc4f314d4bb506de2f219eb70dd959227 neinp/message/write.go -rw-r--r-- 2.0 KiB
280ca11dRuben Schuller update go.mod 1 year, 2 months ago
                                                                                
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
101
102
103
104
105
106
107
108
109
package message

import (
	"git.sr.ht/~rbn/neinp/basic"
	"git.sr.ht/~rbn/neinp/fid"
	"io"
)

/*TWrite requests data to be written to a file.

Write Count bytes of Data at Offset bytes from the beginning
of the file. The file which is represented by Fid must be
opened for writing before this request, when opened in append
mode, the write will be to the end of the file, ignoring Offset.
Writes to directories are forbidden.

See also: http://man.cat-v.org/inferno/5/read
*/
type TWrite struct {
	Fid    fid.Fid
	Offset uint64
	Count  uint32
	Data   []byte
}

func (m *TWrite) encode(w io.Writer) (int64, error) {
	n1, err := basic.Uint32Encode(w, uint32(m.Fid))
	if err != nil {
		return n1, err
	}

	n2, err := basic.Uint64Encode(w, m.Offset)
	if err != nil {
		return n1 + n2, err
	}

	n3, err := basic.Uint32Encode(w, m.Count)
	if err != nil {
		return n1 + n2 + n3, err
	}

	n4, err := w.Write(m.Data)
	if err != nil {
		return n1 + n2 + n3 + int64(n4), err
	}

	return n1 + n2 + n3 + int64(n4), nil
}

func (m *TWrite) decode(r io.Reader) (int64, error) {
	f, n1, err := basic.Uint32Decode(r)
	if err != nil {
		return n1, err
	}

	offset, n2, err := basic.Uint64Decode(r)
	if err != nil {
		return n1 + n2, err
	}

	count, n3, err := basic.Uint32Decode(r)
	if err != nil {
		return n1 + n2 + n3, err
	}

	m.Fid = fid.Fid(f)
	m.Offset = offset
	m.Count = count

	m.Data = make([]byte, count)

	n4, err := r.Read(m.Data)
	if err != nil {
		return n1 + n2 + n3 + int64(n4), err
	}

	return n1 + n2 + n3 + int64(n4), nil
}

/*RWrite is the reply to a TWrite.

Count is the number of bytes written. It usually should be
the same as requested.

See also: http://man.cat-v.org/inferno/5/read
*/
type RWrite struct {
	Count uint32
}

func (m *RWrite) encode(w io.Writer) (int64, error) {
	n, err := basic.Uint32Encode(w, m.Count)
	if err != nil {
		return n, err
	}

	return n, nil
}

func (m *RWrite) decode(r io.Reader) (int64, error) {
	count, n, err := basic.Uint32Decode(r)
	if err != nil {
		return n, err
	}

	m.Count = count

	return n, nil
}