Rietveld Code Review Tool
Help | Bug tracker | Discussion group | Source code | Sign in
(125)

Unified Diff: src/pkg/rpc/server.go

Issue 4889043: code review 4889043: rpc: implement ServeRequest to synchronously serve a si... (Closed)
Patch Set: diff -r de51e6f7dd3e https://go.googlecode.com/hg/ Created 13 years, 7 months ago
Use n/p to move between diff chunks; N/P to move between comments. Please Sign in to add in-line comments.
Jump to:
View side-by-side diff with in-line comments
Download patch
« no previous file with comments | « no previous file | src/pkg/rpc/server_test.go » ('j') | src/pkg/rpc/server_test.go » ('J')
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: src/pkg/rpc/server.go
===================================================================
--- a/src/pkg/rpc/server.go
+++ b/src/pkg/rpc/server.go
@@ -394,7 +394,7 @@
func (server *Server) ServeCodec(codec ServerCodec) {
sending := new(sync.Mutex)
for {
- req, service, mtype, err := server.readRequest(codec)
+ service, mtype, req, argv, replyv, err := server.readRequest(codec)
if err != nil {
if err != os.EOF {
log.Println("rpc:", err)
@@ -402,9 +402,6 @@
if err == os.EOF || err == io.ErrUnexpectedEOF {
break
}
- // discard body
- codec.ReadRequestBody(nil)
-
// send a response if we actually managed to read a header.
if req != nil {
server.sendResponse(sending, req, invalidRequest, codec, err.String())
@@ -412,37 +409,31 @@
}
continue
}
-
- // Decode the argument value.
- var argv reflect.Value
- argIsValue := false // if true, need to indirect before calling.
- if mtype.ArgType.Kind() == reflect.Ptr {
- argv = reflect.New(mtype.ArgType.Elem())
- } else {
- argv = reflect.New(mtype.ArgType)
- argIsValue = true
- }
- // argv guaranteed to be a pointer now.
- replyv := reflect.New(mtype.ReplyType.Elem())
- err = codec.ReadRequestBody(argv.Interface())
- if err != nil {
- if err == os.EOF || err == io.ErrUnexpectedEOF {
- if err == io.ErrUnexpectedEOF {
- log.Println("rpc:", err)
- }
- break
- }
- server.sendResponse(sending, req, replyv.Interface(), codec, err.String())
- continue
- }
- if argIsValue {
- argv = argv.Elem()
- }
go service.call(server, sending, mtype, req, argv, replyv, codec)
}
codec.Close()
}
+// ServeSingle is like ServeCodec but synchronously serves a single request
rsc 2011/08/15 16:11:09 suggest ServeRequest instead of ServeSingle. // S
sougou 2011/08/15 20:17:18 Done.
+// without launching a goroutine. It does not close the codec upon completion.
+func (server *Server) ServeSingle(codec ServerCodec) os.Error {
+ sending := new(sync.Mutex)
+ service, mtype, req, argv, replyv, err := server.readRequest(codec)
+ if err != nil {
+ if err == os.EOF || err == io.ErrUnexpectedEOF {
+ return err
+ }
+ // send a response if we actually managed to read a header.
+ if req != nil {
+ server.sendResponse(sending, req, invalidRequest, codec, err.String())
+ server.freeRequest(req)
+ }
+ return err
+ }
+ service.call(server, sending, mtype, req, argv, replyv, codec)
+ return nil
+}
+
func (server *Server) getRequest() *Request {
server.reqLock.Lock()
req := server.freeReq
@@ -483,7 +474,38 @@
server.respLock.Unlock()
}
-func (server *Server) readRequest(codec ServerCodec) (req *Request, service *service, mtype *methodType, err os.Error) {
+func (server *Server) readRequest(codec ServerCodec) (service *service, mtype *methodType, req *Request, argv, replyv reflect.Value, err os.Error) {
+ service, mtype, req, err = server.readRequestHeader(codec)
+ if err != nil {
+ if err == os.EOF || err == io.ErrUnexpectedEOF {
+ return
+ }
+ // discard body
+ codec.ReadRequestBody(nil)
+ return
+ }
+
+ // Decode the argument value.
+ argIsValue := false // if true, need to indirect before calling.
+ if mtype.ArgType.Kind() == reflect.Ptr {
+ argv = reflect.New(mtype.ArgType.Elem())
+ } else {
+ argv = reflect.New(mtype.ArgType)
+ argIsValue = true
+ }
+ // argv guaranteed to be a pointer now.
+ if err = codec.ReadRequestBody(argv.Interface()); err != nil {
+ return
+ }
+ if argIsValue {
+ argv = argv.Elem()
+ }
+
+ replyv = reflect.New(mtype.ReplyType.Elem())
+ return
+}
+
+func (server *Server) readRequestHeader(codec ServerCodec) (service *service, mtype *methodType, req *Request, err os.Error) {
// Grab the request header.
req = server.getRequest()
err = codec.ReadRequestHeader(req)
@@ -568,6 +590,12 @@
DefaultServer.ServeCodec(codec)
}
+// ServeSingle is like ServeCodec but synchronously serves a single request
rsc 2011/08/15 16:11:09 same
sougou 2011/08/15 20:17:18 Done.
+// without launching a goroutine. It does not close the codec upon completion.
+func ServeSingle(codec ServerCodec) os.Error {
+ return DefaultServer.ServeSingle(codec)
+}
+
// Accept accepts connections on the listener and serves requests
// to DefaultServer for each incoming connection.
// Accept blocks; the caller typically invokes it in a go statement.
« no previous file with comments | « no previous file | src/pkg/rpc/server_test.go » ('j') | src/pkg/rpc/server_test.go » ('J')

Powered by Google App Engine
RSS Feeds Recent Issues | This issue
This is Rietveld f62528b