From 1acc5f70cda9863d2a7bcab756aa14c26ae6de86 Mon Sep 17 00:00:00 2001 From: soypat Date: Sat, 31 May 2025 14:51:30 -0300 Subject: [PATCH] HTTP EXCHANGE SUCCESS --- examples/stackbasic/main.go | 19 +++++++++++++++++-- tcp/handler.go | 31 +++++++++++++++++++++++++------ 2 files changed, 42 insertions(+), 8 deletions(-) diff --git a/examples/stackbasic/main.go b/examples/stackbasic/main.go index ff0a8b5..17350b1 100644 --- a/examples/stackbasic/main.go +++ b/examples/stackbasic/main.go @@ -69,7 +69,7 @@ func main() { log.Fatal(err) } else if nread > 0 { debugEthPacket(nil, "IN ", buf[:nread]) - fmt.Println("INHEX ", debugHex(buf[:nread])) + // fmt.Println("INHEX ", debugHex(buf[:nread])) err = lStack.RecvEth(buf[:nread]) if err != nil { slogger.error("recv", slog.String("err", err.Error()), slog.Int("plen", nread)) @@ -81,7 +81,7 @@ func main() { if err != nil { slogger.error("handle", slog.String("err", err.Error())) } else if nw > 0 { - fmt.Println("OUTHEX ", debugHex(buf[:nread])) + // fmt.Println("OUTHEX ", debugHex(buf[:nread])) _, err = tap.Write(buf[:nw]) if err != nil { log.Fatal(err) @@ -116,6 +116,21 @@ func doHTTP(conn *internet.TCPConn, hdr *httpraw.Header) error { } // HTTP parsed succesfully! fmt.Println("GOT HTTP:\n", hdr.String()) + fmt.Println("sending response...") + hdr.Reset(nil) + hdr.SetStatus("200", "OK") + response, err := hdr.AppendResponse(nil) + if err != nil { + return err + } + _, err = conn.Write(response) + if err != nil { + return err + } + err = conn.Close() + if err != nil { + return err + } return nil } diff --git a/tcp/handler.go b/tcp/handler.go index 07e1eae..1b2b90a 100644 --- a/tcp/handler.go +++ b/tcp/handler.go @@ -192,7 +192,13 @@ func (h *Handler) Recv(incomingPacket []byte) error { func (h *Handler) Close() error { h.trace("tcp.Handler.Close") - return h.scb.Close() + if h.closing { + return errConnectionClosing + } else if h.State().IsClosed() { + return net.ErrClosed + } + h.closing = true + return nil } // Send writes TCP frame to be sent over the network to the remote peer to `b`. @@ -200,14 +206,18 @@ func (h *Handler) Close() error { // The returned integer is the length written to the argument buffer. func (h *Handler) Send(b []byte) (int, error) { h.trace("tcp.Handler:start", slog.Uint64("port", uint64(h.localPort))) - if h.isClosed() && !h.AwaitingSynSend() { + if h.State().IsClosed() && !h.AwaitingSynSend() { return 0, net.ErrClosed } tfrm, err := NewFrame(b) if err != nil { return 0, err } - + buffered := h.bufTx.Buffered() + if buffered == 0 && h.closing { + err = h.scb.Close() + h.info("tcp.Handler:Close", slog.String("scb.Close.err", errstr(err))) + } offset := uint8(5) var segment Segment if h.AwaitingSynSend() { @@ -217,7 +227,7 @@ func (h *Handler) Send(b []byte) (int, error) { offset++ } else { var ok bool - available := min(h.bufTx.Buffered(), len(b)-sizeHeaderTCP) + available := min(buffered, len(b)-sizeHeaderTCP) segment, ok = h.scb.PendingSegment(available) if !ok { // No pending control segment or data to send. Yield. @@ -257,7 +267,9 @@ func (h *Handler) Free() int { // Write implements [io.Writer] by copying b to a internal buffer to be sent over the network on the next // [Handler.Send] call that can send data to remote peer. Use [Handler.Free] to know the maximum length the argument slice can be before erroring. func (h *Handler) Write(b []byte) (int, error) { - if h.State().IsClosed() { // Reject write call if data cannot be sent. + if h.closing { + return 0, errConnectionClosing + } else if h.State().IsClosed() { // Reject write call if data cannot be sent. return 0, net.ErrClosed } return h.bufTx.Write(b) @@ -295,7 +307,7 @@ func (h *Handler) AwaitingSynSend() bool { } func (h *Handler) isClosed() bool { - return h.closing || h.scb.State().IsClosed() + return h.scb.State().IsClosed() } func min(a, b int) int { @@ -304,3 +316,10 @@ func min(a, b int) int { } return b } + +func errstr(err error) string { + if err == nil { + return "" + } + return err.Error() +}