lib9p

Go 9P library.
Log | Files | Refs | LICENSE

commit d00ed1bef534f12831fa61cfface30544097d550
parent aae9422cc1c248755223104fbefda57e1aa40554
Author: Matsuda Kenji <info@mtkn.jp>
Date:   Wed, 27 Dec 2023 15:03:25 +0900

add TestSAuth

Diffstat:
Mserver.go | 5+++++
Mserver2_test.go | 90+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++----
2 files changed, 91 insertions(+), 4 deletions(-)

diff --git a/server.go b/server.go @@ -255,6 +255,11 @@ func sAuth(ctx context.Context, s *Server, c <-chan *Req) { } ifcall := r.Ifcall.(*TAuth) var err error + if ifcall.Afid == NOFID { + setError(r, fmt.Errorf("NOFID can't be used for afid")) // TODO: really? + s.respChan <- r + continue + } r.Afid, err = s.fPool.add(ifcall.Afid) if err != nil { setError(r, ErrDupFid) diff --git a/server2_test.go b/server2_test.go @@ -3,6 +3,7 @@ package lib9p import ( "bytes" "context" + "errors" "io" "os" "reflect" @@ -52,10 +53,6 @@ func TestRunListener(t *testing.T) { want, got) } } - cancel() - if _, ok := <-s.listenChan; ok { - t.Error("listenChan not closed") - } } // TestRunSpeaker tests if the speaker goroutine receives 9P messages @@ -109,6 +106,7 @@ func TestGetReq(t *testing.T) { s := &Server{r: tFile, rPool: newReqPool()} for { ctx, cancel := context.WithCancel(context.Background()) + defer cancel() // in case error. got := s.getReq(ctx) if got.listenErr == io.EOF { break @@ -182,4 +180,88 @@ func TestSVersion(t *testing.T) { } s.msize = oldMsize } +} + +func TestSAuth(t *testing.T) { + tests := []struct{ + input *Req + want *Req + authFunc func(context.Context, chan<- *Req) chan<- *Req + }{ + {&Req{Ifcall: &TAuth{Afid: NOFID, Uname: "kenji", Aname: ""}}, + &Req{Ofcall: &RError{Ename: errors.New("authentication not required")}}, nil}, + {&Req{Ifcall: &TAuth{Afid: NOFID, Uname: "kenji", Aname: ""}}, + &Req{Ofcall: &RError{Ename: errors.New("NOFID can't be used for afid")}}, + func(ctx context.Context, respc chan<- *Req) chan<- *Req { + authc := make(chan *Req) + go func() { + for { + select { + case r, ok := <-authc: + if !ok { + return + } + respc <- r + case <-ctx.Done(): + return + } + } + }() + return authc + }}, + {&Req{Ifcall: &TAuth{Afid: 0, Uname: "kenji", Aname: ""}}, + &Req{Ofcall: &RAuth{Tag: 0, Aqid: Qid{0, 1, 2}}}, + func(ctx context.Context, respc chan<- *Req) chan<- *Req { + authc := make(chan *Req) + go func() { + for { + select { + case r, ok := <-authc: + if !ok { + return + } + r.Ofcall = &RAuth{Tag: 0, Aqid: Qid{0, 1, 2}} + respc <- r + case <-ctx.Done(): + return + } + } + }() + return authc + }}, + } + for _, test := range tests { + func () { + tc := make(chan *Req) + rc := make(chan *Req) + defer close(tc) + defer close(rc) + s := &Server{respChan: rc, Auth: test.authFunc, fPool: newFidPool()} + ctx, cancel := context.WithCancel(context.Background()) + defer cancel() + go sAuth(ctx, s, tc) + tc <- test.input + ofcall := (<-rc).Ofcall + switch wantmsg := test.want.Ofcall.(type) { + case *RAuth: + gotmsg, ok := ofcall.(*RAuth) + if !ok { + t.Errorf("unexpected message: %v", ofcall) + return + } + if !reflect.DeepEqual(wantmsg, gotmsg) { + t.Errorf("want: %v,\n\tgot: %v", wantmsg, gotmsg) + return + } + case *RError: + _, ok := ofcall.(*RError) + if !ok { + t.Errorf("unexpected message: %v", ofcall) + return + } + default: + t.Fatalf("unexpected message: %v", wantmsg) + } + }() + } } \ No newline at end of file