Add rootfs service
Add rootfs service to allow creation of rootfs from layer array Signed-off-by: Derek McGowan <derek@mcgstyle.net> (github: dmcgowan)
This commit is contained in:
		
							parent
							
								
									5c69a7fd6d
								
							
						
					
					
						commit
						ead425f426
					
				
					 8 changed files with 1182 additions and 6 deletions
				
			
		
							
								
								
									
										577
									
								
								api/services/rootfs/rootfs.pb.go
									
										
									
									
									
										Normal file
									
								
							
							
						
						
									
										577
									
								
								api/services/rootfs/rootfs.pb.go
									
										
									
									
									
										Normal file
									
								
							|  | @ -0,0 +1,577 @@ | ||||||
|  | // Code generated by protoc-gen-gogo. | ||||||
|  | // source: github.com/docker/containerd/api/services/rootfs/rootfs.proto | ||||||
|  | // DO NOT EDIT! | ||||||
|  | 
 | ||||||
|  | /* | ||||||
|  | 	Package rootfs is a generated protocol buffer package. | ||||||
|  | 
 | ||||||
|  | 	It is generated from these files: | ||||||
|  | 		github.com/docker/containerd/api/services/rootfs/rootfs.proto | ||||||
|  | 
 | ||||||
|  | 	It has these top-level messages: | ||||||
|  | 		PrepareRequest | ||||||
|  | 		PrepareResponse | ||||||
|  | */ | ||||||
|  | package rootfs | ||||||
|  | 
 | ||||||
|  | import proto "github.com/gogo/protobuf/proto" | ||||||
|  | import fmt "fmt" | ||||||
|  | import math "math" | ||||||
|  | import _ "github.com/gogo/protobuf/gogoproto" | ||||||
|  | import _ "github.com/golang/protobuf/ptypes/empty" | ||||||
|  | import _ "github.com/docker/containerd/api/types/mount" | ||||||
|  | import containerd_v1_types1 "github.com/docker/containerd/api/types/descriptor" | ||||||
|  | 
 | ||||||
|  | import github_com_opencontainers_go_digest "github.com/opencontainers/go-digest" | ||||||
|  | 
 | ||||||
|  | import ( | ||||||
|  | 	context "golang.org/x/net/context" | ||||||
|  | 	grpc "google.golang.org/grpc" | ||||||
|  | ) | ||||||
|  | 
 | ||||||
|  | import strings "strings" | ||||||
|  | import reflect "reflect" | ||||||
|  | 
 | ||||||
|  | import io "io" | ||||||
|  | 
 | ||||||
|  | // Reference imports to suppress errors if they are not otherwise used. | ||||||
|  | var _ = proto.Marshal | ||||||
|  | var _ = fmt.Errorf | ||||||
|  | var _ = math.Inf | ||||||
|  | 
 | ||||||
|  | // This is a compile-time assertion to ensure that this generated file | ||||||
|  | // is compatible with the proto package it is being compiled against. | ||||||
|  | // A compilation error at this line likely means your copy of the | ||||||
|  | // proto package needs to be updated. | ||||||
|  | const _ = proto.GoGoProtoPackageIsVersion2 // please upgrade the proto package | ||||||
|  | 
 | ||||||
|  | type PrepareRequest struct { | ||||||
|  | 	Layers []*containerd_v1_types1.Descriptor `protobuf:"bytes,1,rep,name=layers" json:"layers,omitempty"` | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | func (m *PrepareRequest) Reset()                    { *m = PrepareRequest{} } | ||||||
|  | func (*PrepareRequest) ProtoMessage()               {} | ||||||
|  | func (*PrepareRequest) Descriptor() ([]byte, []int) { return fileDescriptorRootfs, []int{0} } | ||||||
|  | 
 | ||||||
|  | type PrepareResponse struct { | ||||||
|  | 	ChainID github_com_opencontainers_go_digest.Digest `protobuf:"bytes,1,opt,name=chainid,proto3,customtype=github.com/opencontainers/go-digest.Digest" json:"chainid"` | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | func (m *PrepareResponse) Reset()                    { *m = PrepareResponse{} } | ||||||
|  | func (*PrepareResponse) ProtoMessage()               {} | ||||||
|  | func (*PrepareResponse) Descriptor() ([]byte, []int) { return fileDescriptorRootfs, []int{1} } | ||||||
|  | 
 | ||||||
|  | func init() { | ||||||
|  | 	proto.RegisterType((*PrepareRequest)(nil), "containerd.v1.PrepareRequest") | ||||||
|  | 	proto.RegisterType((*PrepareResponse)(nil), "containerd.v1.PrepareResponse") | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | // Reference imports to suppress errors if they are not otherwise used. | ||||||
|  | var _ context.Context | ||||||
|  | var _ grpc.ClientConn | ||||||
|  | 
 | ||||||
|  | // This is a compile-time assertion to ensure that this generated file | ||||||
|  | // is compatible with the grpc package it is being compiled against. | ||||||
|  | const _ = grpc.SupportPackageIsVersion4 | ||||||
|  | 
 | ||||||
|  | // Client API for RootFS service | ||||||
|  | 
 | ||||||
|  | type RootFSClient interface { | ||||||
|  | 	Prepare(ctx context.Context, in *PrepareRequest, opts ...grpc.CallOption) (*PrepareResponse, error) | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | type rootFSClient struct { | ||||||
|  | 	cc *grpc.ClientConn | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | func NewRootFSClient(cc *grpc.ClientConn) RootFSClient { | ||||||
|  | 	return &rootFSClient{cc} | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | func (c *rootFSClient) Prepare(ctx context.Context, in *PrepareRequest, opts ...grpc.CallOption) (*PrepareResponse, error) { | ||||||
|  | 	out := new(PrepareResponse) | ||||||
|  | 	err := grpc.Invoke(ctx, "/containerd.v1.RootFS/Prepare", in, out, c.cc, opts...) | ||||||
|  | 	if err != nil { | ||||||
|  | 		return nil, err | ||||||
|  | 	} | ||||||
|  | 	return out, nil | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | // Server API for RootFS service | ||||||
|  | 
 | ||||||
|  | type RootFSServer interface { | ||||||
|  | 	Prepare(context.Context, *PrepareRequest) (*PrepareResponse, error) | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | func RegisterRootFSServer(s *grpc.Server, srv RootFSServer) { | ||||||
|  | 	s.RegisterService(&_RootFS_serviceDesc, srv) | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | func _RootFS_Prepare_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) { | ||||||
|  | 	in := new(PrepareRequest) | ||||||
|  | 	if err := dec(in); err != nil { | ||||||
|  | 		return nil, err | ||||||
|  | 	} | ||||||
|  | 	if interceptor == nil { | ||||||
|  | 		return srv.(RootFSServer).Prepare(ctx, in) | ||||||
|  | 	} | ||||||
|  | 	info := &grpc.UnaryServerInfo{ | ||||||
|  | 		Server:     srv, | ||||||
|  | 		FullMethod: "/containerd.v1.RootFS/Prepare", | ||||||
|  | 	} | ||||||
|  | 	handler := func(ctx context.Context, req interface{}) (interface{}, error) { | ||||||
|  | 		return srv.(RootFSServer).Prepare(ctx, req.(*PrepareRequest)) | ||||||
|  | 	} | ||||||
|  | 	return interceptor(ctx, in, info, handler) | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | var _RootFS_serviceDesc = grpc.ServiceDesc{ | ||||||
|  | 	ServiceName: "containerd.v1.RootFS", | ||||||
|  | 	HandlerType: (*RootFSServer)(nil), | ||||||
|  | 	Methods: []grpc.MethodDesc{ | ||||||
|  | 		{ | ||||||
|  | 			MethodName: "Prepare", | ||||||
|  | 			Handler:    _RootFS_Prepare_Handler, | ||||||
|  | 		}, | ||||||
|  | 	}, | ||||||
|  | 	Streams:  []grpc.StreamDesc{}, | ||||||
|  | 	Metadata: "github.com/docker/containerd/api/services/rootfs/rootfs.proto", | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | func (m *PrepareRequest) Marshal() (dAtA []byte, err error) { | ||||||
|  | 	size := m.Size() | ||||||
|  | 	dAtA = make([]byte, size) | ||||||
|  | 	n, err := m.MarshalTo(dAtA) | ||||||
|  | 	if err != nil { | ||||||
|  | 		return nil, err | ||||||
|  | 	} | ||||||
|  | 	return dAtA[:n], nil | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | func (m *PrepareRequest) MarshalTo(dAtA []byte) (int, error) { | ||||||
|  | 	var i int | ||||||
|  | 	_ = i | ||||||
|  | 	var l int | ||||||
|  | 	_ = l | ||||||
|  | 	if len(m.Layers) > 0 { | ||||||
|  | 		for _, msg := range m.Layers { | ||||||
|  | 			dAtA[i] = 0xa | ||||||
|  | 			i++ | ||||||
|  | 			i = encodeVarintRootfs(dAtA, i, uint64(msg.Size())) | ||||||
|  | 			n, err := msg.MarshalTo(dAtA[i:]) | ||||||
|  | 			if err != nil { | ||||||
|  | 				return 0, err | ||||||
|  | 			} | ||||||
|  | 			i += n | ||||||
|  | 		} | ||||||
|  | 	} | ||||||
|  | 	return i, nil | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | func (m *PrepareResponse) Marshal() (dAtA []byte, err error) { | ||||||
|  | 	size := m.Size() | ||||||
|  | 	dAtA = make([]byte, size) | ||||||
|  | 	n, err := m.MarshalTo(dAtA) | ||||||
|  | 	if err != nil { | ||||||
|  | 		return nil, err | ||||||
|  | 	} | ||||||
|  | 	return dAtA[:n], nil | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | func (m *PrepareResponse) MarshalTo(dAtA []byte) (int, error) { | ||||||
|  | 	var i int | ||||||
|  | 	_ = i | ||||||
|  | 	var l int | ||||||
|  | 	_ = l | ||||||
|  | 	if len(m.ChainID) > 0 { | ||||||
|  | 		dAtA[i] = 0xa | ||||||
|  | 		i++ | ||||||
|  | 		i = encodeVarintRootfs(dAtA, i, uint64(len(m.ChainID))) | ||||||
|  | 		i += copy(dAtA[i:], m.ChainID) | ||||||
|  | 	} | ||||||
|  | 	return i, nil | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | func encodeFixed64Rootfs(dAtA []byte, offset int, v uint64) int { | ||||||
|  | 	dAtA[offset] = uint8(v) | ||||||
|  | 	dAtA[offset+1] = uint8(v >> 8) | ||||||
|  | 	dAtA[offset+2] = uint8(v >> 16) | ||||||
|  | 	dAtA[offset+3] = uint8(v >> 24) | ||||||
|  | 	dAtA[offset+4] = uint8(v >> 32) | ||||||
|  | 	dAtA[offset+5] = uint8(v >> 40) | ||||||
|  | 	dAtA[offset+6] = uint8(v >> 48) | ||||||
|  | 	dAtA[offset+7] = uint8(v >> 56) | ||||||
|  | 	return offset + 8 | ||||||
|  | } | ||||||
|  | func encodeFixed32Rootfs(dAtA []byte, offset int, v uint32) int { | ||||||
|  | 	dAtA[offset] = uint8(v) | ||||||
|  | 	dAtA[offset+1] = uint8(v >> 8) | ||||||
|  | 	dAtA[offset+2] = uint8(v >> 16) | ||||||
|  | 	dAtA[offset+3] = uint8(v >> 24) | ||||||
|  | 	return offset + 4 | ||||||
|  | } | ||||||
|  | func encodeVarintRootfs(dAtA []byte, offset int, v uint64) int { | ||||||
|  | 	for v >= 1<<7 { | ||||||
|  | 		dAtA[offset] = uint8(v&0x7f | 0x80) | ||||||
|  | 		v >>= 7 | ||||||
|  | 		offset++ | ||||||
|  | 	} | ||||||
|  | 	dAtA[offset] = uint8(v) | ||||||
|  | 	return offset + 1 | ||||||
|  | } | ||||||
|  | func (m *PrepareRequest) Size() (n int) { | ||||||
|  | 	var l int | ||||||
|  | 	_ = l | ||||||
|  | 	if len(m.Layers) > 0 { | ||||||
|  | 		for _, e := range m.Layers { | ||||||
|  | 			l = e.Size() | ||||||
|  | 			n += 1 + l + sovRootfs(uint64(l)) | ||||||
|  | 		} | ||||||
|  | 	} | ||||||
|  | 	return n | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | func (m *PrepareResponse) Size() (n int) { | ||||||
|  | 	var l int | ||||||
|  | 	_ = l | ||||||
|  | 	l = len(m.ChainID) | ||||||
|  | 	if l > 0 { | ||||||
|  | 		n += 1 + l + sovRootfs(uint64(l)) | ||||||
|  | 	} | ||||||
|  | 	return n | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | func sovRootfs(x uint64) (n int) { | ||||||
|  | 	for { | ||||||
|  | 		n++ | ||||||
|  | 		x >>= 7 | ||||||
|  | 		if x == 0 { | ||||||
|  | 			break | ||||||
|  | 		} | ||||||
|  | 	} | ||||||
|  | 	return n | ||||||
|  | } | ||||||
|  | func sozRootfs(x uint64) (n int) { | ||||||
|  | 	return sovRootfs(uint64((x << 1) ^ uint64((int64(x) >> 63)))) | ||||||
|  | } | ||||||
|  | func (this *PrepareRequest) String() string { | ||||||
|  | 	if this == nil { | ||||||
|  | 		return "nil" | ||||||
|  | 	} | ||||||
|  | 	s := strings.Join([]string{`&PrepareRequest{`, | ||||||
|  | 		`Layers:` + strings.Replace(fmt.Sprintf("%v", this.Layers), "Descriptor", "containerd_v1_types1.Descriptor", 1) + `,`, | ||||||
|  | 		`}`, | ||||||
|  | 	}, "") | ||||||
|  | 	return s | ||||||
|  | } | ||||||
|  | func (this *PrepareResponse) String() string { | ||||||
|  | 	if this == nil { | ||||||
|  | 		return "nil" | ||||||
|  | 	} | ||||||
|  | 	s := strings.Join([]string{`&PrepareResponse{`, | ||||||
|  | 		`ChainID:` + fmt.Sprintf("%v", this.ChainID) + `,`, | ||||||
|  | 		`}`, | ||||||
|  | 	}, "") | ||||||
|  | 	return s | ||||||
|  | } | ||||||
|  | func valueToStringRootfs(v interface{}) string { | ||||||
|  | 	rv := reflect.ValueOf(v) | ||||||
|  | 	if rv.IsNil() { | ||||||
|  | 		return "nil" | ||||||
|  | 	} | ||||||
|  | 	pv := reflect.Indirect(rv).Interface() | ||||||
|  | 	return fmt.Sprintf("*%v", pv) | ||||||
|  | } | ||||||
|  | func (m *PrepareRequest) Unmarshal(dAtA []byte) error { | ||||||
|  | 	l := len(dAtA) | ||||||
|  | 	iNdEx := 0 | ||||||
|  | 	for iNdEx < l { | ||||||
|  | 		preIndex := iNdEx | ||||||
|  | 		var wire uint64 | ||||||
|  | 		for shift := uint(0); ; shift += 7 { | ||||||
|  | 			if shift >= 64 { | ||||||
|  | 				return ErrIntOverflowRootfs | ||||||
|  | 			} | ||||||
|  | 			if iNdEx >= l { | ||||||
|  | 				return io.ErrUnexpectedEOF | ||||||
|  | 			} | ||||||
|  | 			b := dAtA[iNdEx] | ||||||
|  | 			iNdEx++ | ||||||
|  | 			wire |= (uint64(b) & 0x7F) << shift | ||||||
|  | 			if b < 0x80 { | ||||||
|  | 				break | ||||||
|  | 			} | ||||||
|  | 		} | ||||||
|  | 		fieldNum := int32(wire >> 3) | ||||||
|  | 		wireType := int(wire & 0x7) | ||||||
|  | 		if wireType == 4 { | ||||||
|  | 			return fmt.Errorf("proto: PrepareRequest: wiretype end group for non-group") | ||||||
|  | 		} | ||||||
|  | 		if fieldNum <= 0 { | ||||||
|  | 			return fmt.Errorf("proto: PrepareRequest: illegal tag %d (wire type %d)", fieldNum, wire) | ||||||
|  | 		} | ||||||
|  | 		switch fieldNum { | ||||||
|  | 		case 1: | ||||||
|  | 			if wireType != 2 { | ||||||
|  | 				return fmt.Errorf("proto: wrong wireType = %d for field Layers", wireType) | ||||||
|  | 			} | ||||||
|  | 			var msglen int | ||||||
|  | 			for shift := uint(0); ; shift += 7 { | ||||||
|  | 				if shift >= 64 { | ||||||
|  | 					return ErrIntOverflowRootfs | ||||||
|  | 				} | ||||||
|  | 				if iNdEx >= l { | ||||||
|  | 					return io.ErrUnexpectedEOF | ||||||
|  | 				} | ||||||
|  | 				b := dAtA[iNdEx] | ||||||
|  | 				iNdEx++ | ||||||
|  | 				msglen |= (int(b) & 0x7F) << shift | ||||||
|  | 				if b < 0x80 { | ||||||
|  | 					break | ||||||
|  | 				} | ||||||
|  | 			} | ||||||
|  | 			if msglen < 0 { | ||||||
|  | 				return ErrInvalidLengthRootfs | ||||||
|  | 			} | ||||||
|  | 			postIndex := iNdEx + msglen | ||||||
|  | 			if postIndex > l { | ||||||
|  | 				return io.ErrUnexpectedEOF | ||||||
|  | 			} | ||||||
|  | 			m.Layers = append(m.Layers, &containerd_v1_types1.Descriptor{}) | ||||||
|  | 			if err := m.Layers[len(m.Layers)-1].Unmarshal(dAtA[iNdEx:postIndex]); err != nil { | ||||||
|  | 				return err | ||||||
|  | 			} | ||||||
|  | 			iNdEx = postIndex | ||||||
|  | 		default: | ||||||
|  | 			iNdEx = preIndex | ||||||
|  | 			skippy, err := skipRootfs(dAtA[iNdEx:]) | ||||||
|  | 			if err != nil { | ||||||
|  | 				return err | ||||||
|  | 			} | ||||||
|  | 			if skippy < 0 { | ||||||
|  | 				return ErrInvalidLengthRootfs | ||||||
|  | 			} | ||||||
|  | 			if (iNdEx + skippy) > l { | ||||||
|  | 				return io.ErrUnexpectedEOF | ||||||
|  | 			} | ||||||
|  | 			iNdEx += skippy | ||||||
|  | 		} | ||||||
|  | 	} | ||||||
|  | 
 | ||||||
|  | 	if iNdEx > l { | ||||||
|  | 		return io.ErrUnexpectedEOF | ||||||
|  | 	} | ||||||
|  | 	return nil | ||||||
|  | } | ||||||
|  | func (m *PrepareResponse) Unmarshal(dAtA []byte) error { | ||||||
|  | 	l := len(dAtA) | ||||||
|  | 	iNdEx := 0 | ||||||
|  | 	for iNdEx < l { | ||||||
|  | 		preIndex := iNdEx | ||||||
|  | 		var wire uint64 | ||||||
|  | 		for shift := uint(0); ; shift += 7 { | ||||||
|  | 			if shift >= 64 { | ||||||
|  | 				return ErrIntOverflowRootfs | ||||||
|  | 			} | ||||||
|  | 			if iNdEx >= l { | ||||||
|  | 				return io.ErrUnexpectedEOF | ||||||
|  | 			} | ||||||
|  | 			b := dAtA[iNdEx] | ||||||
|  | 			iNdEx++ | ||||||
|  | 			wire |= (uint64(b) & 0x7F) << shift | ||||||
|  | 			if b < 0x80 { | ||||||
|  | 				break | ||||||
|  | 			} | ||||||
|  | 		} | ||||||
|  | 		fieldNum := int32(wire >> 3) | ||||||
|  | 		wireType := int(wire & 0x7) | ||||||
|  | 		if wireType == 4 { | ||||||
|  | 			return fmt.Errorf("proto: PrepareResponse: wiretype end group for non-group") | ||||||
|  | 		} | ||||||
|  | 		if fieldNum <= 0 { | ||||||
|  | 			return fmt.Errorf("proto: PrepareResponse: illegal tag %d (wire type %d)", fieldNum, wire) | ||||||
|  | 		} | ||||||
|  | 		switch fieldNum { | ||||||
|  | 		case 1: | ||||||
|  | 			if wireType != 2 { | ||||||
|  | 				return fmt.Errorf("proto: wrong wireType = %d for field ChainID", wireType) | ||||||
|  | 			} | ||||||
|  | 			var stringLen uint64 | ||||||
|  | 			for shift := uint(0); ; shift += 7 { | ||||||
|  | 				if shift >= 64 { | ||||||
|  | 					return ErrIntOverflowRootfs | ||||||
|  | 				} | ||||||
|  | 				if iNdEx >= l { | ||||||
|  | 					return io.ErrUnexpectedEOF | ||||||
|  | 				} | ||||||
|  | 				b := dAtA[iNdEx] | ||||||
|  | 				iNdEx++ | ||||||
|  | 				stringLen |= (uint64(b) & 0x7F) << shift | ||||||
|  | 				if b < 0x80 { | ||||||
|  | 					break | ||||||
|  | 				} | ||||||
|  | 			} | ||||||
|  | 			intStringLen := int(stringLen) | ||||||
|  | 			if intStringLen < 0 { | ||||||
|  | 				return ErrInvalidLengthRootfs | ||||||
|  | 			} | ||||||
|  | 			postIndex := iNdEx + intStringLen | ||||||
|  | 			if postIndex > l { | ||||||
|  | 				return io.ErrUnexpectedEOF | ||||||
|  | 			} | ||||||
|  | 			m.ChainID = github_com_opencontainers_go_digest.Digest(dAtA[iNdEx:postIndex]) | ||||||
|  | 			iNdEx = postIndex | ||||||
|  | 		default: | ||||||
|  | 			iNdEx = preIndex | ||||||
|  | 			skippy, err := skipRootfs(dAtA[iNdEx:]) | ||||||
|  | 			if err != nil { | ||||||
|  | 				return err | ||||||
|  | 			} | ||||||
|  | 			if skippy < 0 { | ||||||
|  | 				return ErrInvalidLengthRootfs | ||||||
|  | 			} | ||||||
|  | 			if (iNdEx + skippy) > l { | ||||||
|  | 				return io.ErrUnexpectedEOF | ||||||
|  | 			} | ||||||
|  | 			iNdEx += skippy | ||||||
|  | 		} | ||||||
|  | 	} | ||||||
|  | 
 | ||||||
|  | 	if iNdEx > l { | ||||||
|  | 		return io.ErrUnexpectedEOF | ||||||
|  | 	} | ||||||
|  | 	return nil | ||||||
|  | } | ||||||
|  | func skipRootfs(dAtA []byte) (n int, err error) { | ||||||
|  | 	l := len(dAtA) | ||||||
|  | 	iNdEx := 0 | ||||||
|  | 	for iNdEx < l { | ||||||
|  | 		var wire uint64 | ||||||
|  | 		for shift := uint(0); ; shift += 7 { | ||||||
|  | 			if shift >= 64 { | ||||||
|  | 				return 0, ErrIntOverflowRootfs | ||||||
|  | 			} | ||||||
|  | 			if iNdEx >= l { | ||||||
|  | 				return 0, io.ErrUnexpectedEOF | ||||||
|  | 			} | ||||||
|  | 			b := dAtA[iNdEx] | ||||||
|  | 			iNdEx++ | ||||||
|  | 			wire |= (uint64(b) & 0x7F) << shift | ||||||
|  | 			if b < 0x80 { | ||||||
|  | 				break | ||||||
|  | 			} | ||||||
|  | 		} | ||||||
|  | 		wireType := int(wire & 0x7) | ||||||
|  | 		switch wireType { | ||||||
|  | 		case 0: | ||||||
|  | 			for shift := uint(0); ; shift += 7 { | ||||||
|  | 				if shift >= 64 { | ||||||
|  | 					return 0, ErrIntOverflowRootfs | ||||||
|  | 				} | ||||||
|  | 				if iNdEx >= l { | ||||||
|  | 					return 0, io.ErrUnexpectedEOF | ||||||
|  | 				} | ||||||
|  | 				iNdEx++ | ||||||
|  | 				if dAtA[iNdEx-1] < 0x80 { | ||||||
|  | 					break | ||||||
|  | 				} | ||||||
|  | 			} | ||||||
|  | 			return iNdEx, nil | ||||||
|  | 		case 1: | ||||||
|  | 			iNdEx += 8 | ||||||
|  | 			return iNdEx, nil | ||||||
|  | 		case 2: | ||||||
|  | 			var length int | ||||||
|  | 			for shift := uint(0); ; shift += 7 { | ||||||
|  | 				if shift >= 64 { | ||||||
|  | 					return 0, ErrIntOverflowRootfs | ||||||
|  | 				} | ||||||
|  | 				if iNdEx >= l { | ||||||
|  | 					return 0, io.ErrUnexpectedEOF | ||||||
|  | 				} | ||||||
|  | 				b := dAtA[iNdEx] | ||||||
|  | 				iNdEx++ | ||||||
|  | 				length |= (int(b) & 0x7F) << shift | ||||||
|  | 				if b < 0x80 { | ||||||
|  | 					break | ||||||
|  | 				} | ||||||
|  | 			} | ||||||
|  | 			iNdEx += length | ||||||
|  | 			if length < 0 { | ||||||
|  | 				return 0, ErrInvalidLengthRootfs | ||||||
|  | 			} | ||||||
|  | 			return iNdEx, nil | ||||||
|  | 		case 3: | ||||||
|  | 			for { | ||||||
|  | 				var innerWire uint64 | ||||||
|  | 				var start int = iNdEx | ||||||
|  | 				for shift := uint(0); ; shift += 7 { | ||||||
|  | 					if shift >= 64 { | ||||||
|  | 						return 0, ErrIntOverflowRootfs | ||||||
|  | 					} | ||||||
|  | 					if iNdEx >= l { | ||||||
|  | 						return 0, io.ErrUnexpectedEOF | ||||||
|  | 					} | ||||||
|  | 					b := dAtA[iNdEx] | ||||||
|  | 					iNdEx++ | ||||||
|  | 					innerWire |= (uint64(b) & 0x7F) << shift | ||||||
|  | 					if b < 0x80 { | ||||||
|  | 						break | ||||||
|  | 					} | ||||||
|  | 				} | ||||||
|  | 				innerWireType := int(innerWire & 0x7) | ||||||
|  | 				if innerWireType == 4 { | ||||||
|  | 					break | ||||||
|  | 				} | ||||||
|  | 				next, err := skipRootfs(dAtA[start:]) | ||||||
|  | 				if err != nil { | ||||||
|  | 					return 0, err | ||||||
|  | 				} | ||||||
|  | 				iNdEx = start + next | ||||||
|  | 			} | ||||||
|  | 			return iNdEx, nil | ||||||
|  | 		case 4: | ||||||
|  | 			return iNdEx, nil | ||||||
|  | 		case 5: | ||||||
|  | 			iNdEx += 4 | ||||||
|  | 			return iNdEx, nil | ||||||
|  | 		default: | ||||||
|  | 			return 0, fmt.Errorf("proto: illegal wireType %d", wireType) | ||||||
|  | 		} | ||||||
|  | 	} | ||||||
|  | 	panic("unreachable") | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | var ( | ||||||
|  | 	ErrInvalidLengthRootfs = fmt.Errorf("proto: negative length found during unmarshaling") | ||||||
|  | 	ErrIntOverflowRootfs   = fmt.Errorf("proto: integer overflow") | ||||||
|  | ) | ||||||
|  | 
 | ||||||
|  | func init() { | ||||||
|  | 	proto.RegisterFile("github.com/docker/containerd/api/services/rootfs/rootfs.proto", fileDescriptorRootfs) | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | var fileDescriptorRootfs = []byte{ | ||||||
|  | 	// 335 bytes of a gzipped FileDescriptorProto | ||||||
|  | 	0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0x8c, 0x90, 0xc1, 0x4f, 0xea, 0x40, | ||||||
|  | 	0x10, 0xc6, 0xd9, 0xbc, 0x04, 0xf2, 0xf6, 0xe5, 0xbd, 0x97, 0x34, 0x1e, 0x08, 0xc6, 0x2d, 0xe1, | ||||||
|  | 	0x44, 0x4c, 0xdc, 0x8d, 0x78, 0xd0, 0x0b, 0x17, 0x24, 0x46, 0x6e, 0xa6, 0x1e, 0x3c, 0x97, 0x76, | ||||||
|  | 	0x58, 0x56, 0xa1, 0xb3, 0xee, 0x6e, 0x49, 0xb8, 0xf9, 0xe7, 0x71, 0xf4, 0x68, 0x3c, 0x10, 0xe9, | ||||||
|  | 	0x5f, 0x62, 0x68, 0x0b, 0x82, 0x89, 0xd1, 0x4b, 0x67, 0x9a, 0xef, 0x9b, 0xdf, 0x7c, 0xb3, 0xb4, | ||||||
|  | 	0x2b, 0x95, 0x1b, 0xa7, 0x43, 0x1e, 0xe1, 0x54, 0xc4, 0x18, 0x3d, 0x80, 0x11, 0x11, 0x26, 0x2e, | ||||||
|  | 	0x54, 0x09, 0x98, 0x58, 0x84, 0x5a, 0x09, 0x0b, 0x66, 0xa6, 0x22, 0xb0, 0xc2, 0x20, 0xba, 0xd1, | ||||||
|  | 	0xa6, 0x70, 0x6d, 0xd0, 0xa1, 0xf7, 0xf7, 0xc3, 0xcc, 0x67, 0xa7, 0x8d, 0x03, 0x89, 0x12, 0x73, | ||||||
|  | 	0x45, 0xac, 0xbb, 0xc2, 0xd4, 0x38, 0x94, 0x88, 0x72, 0x02, 0x22, 0xff, 0x1b, 0xa6, 0x23, 0x01, | ||||||
|  | 	0x53, 0xed, 0xe6, 0xa5, 0x78, 0xf1, 0x6d, 0x00, 0x37, 0xd7, 0x60, 0xc5, 0x14, 0xd3, 0xc4, 0x15, | ||||||
|  | 	0xdf, 0x72, 0xb2, 0xf7, 0xc3, 0xc9, 0x18, 0x6c, 0x64, 0x94, 0x76, 0x68, 0x76, 0xda, 0x82, 0xd1, | ||||||
|  | 	0x1a, 0xd0, 0x7f, 0x37, 0x06, 0x74, 0x68, 0x20, 0x80, 0xc7, 0x14, 0xac, 0xf3, 0xce, 0x69, 0x75, | ||||||
|  | 	0x12, 0xce, 0xc1, 0xd8, 0x3a, 0x69, 0xfe, 0x6a, 0xff, 0xe9, 0xf8, 0x7c, 0xef, 0x44, 0x9e, 0x33, | ||||||
|  | 	0x79, 0x7f, 0x0b, 0x0a, 0x4a, 0x7b, 0xeb, 0x9e, 0xfe, 0xdf, 0xa2, 0xac, 0xc6, 0xc4, 0x82, 0x77, | ||||||
|  | 	0x47, 0x6b, 0xd1, 0x38, 0x54, 0x89, 0x8a, 0xeb, 0xa4, 0x49, 0xda, 0xbf, 0x7b, 0xdd, 0xc5, 0xd2, | ||||||
|  | 	0xaf, 0xbc, 0x2e, 0xfd, 0xe3, 0x9d, 0xe8, 0xa8, 0x21, 0xd9, 0xae, 0xb0, 0x42, 0xe2, 0x49, 0xac, | ||||||
|  | 	0x24, 0x58, 0xc7, 0xfb, 0x79, 0xc9, 0x96, 0x7e, 0xed, 0x72, 0x0d, 0x19, 0xf4, 0x83, 0x0d, 0xad, | ||||||
|  | 	0x13, 0xd0, 0x6a, 0x80, 0xe8, 0xae, 0x6e, 0xbd, 0x6b, 0x5a, 0x2b, 0xb7, 0x7a, 0x47, 0x9f, 0x92, | ||||||
|  | 	0xee, 0x1f, 0xd6, 0x60, 0x5f, 0xc9, 0x45, 0xd8, 0x5e, 0x7d, 0xb1, 0x62, 0x95, 0x97, 0x15, 0xab, | ||||||
|  | 	0x3c, 0x65, 0x8c, 0x2c, 0x32, 0x46, 0x9e, 0x33, 0x46, 0xde, 0x32, 0x46, 0x86, 0xd5, 0xfc, 0xad, | ||||||
|  | 	0xce, 0xde, 0x03, 0x00, 0x00, 0xff, 0xff, 0x4c, 0xa2, 0x59, 0x7e, 0x2c, 0x02, 0x00, 0x00, | ||||||
|  | } | ||||||
							
								
								
									
										38
									
								
								api/services/rootfs/rootfs.proto
									
										
									
									
									
										Normal file
									
								
							
							
						
						
									
										38
									
								
								api/services/rootfs/rootfs.proto
									
										
									
									
									
										Normal file
									
								
							|  | @ -0,0 +1,38 @@ | ||||||
|  | syntax = "proto3"; | ||||||
|  | 
 | ||||||
|  | package containerd.v1; | ||||||
|  | 
 | ||||||
|  | import "gogoproto/gogo.proto"; | ||||||
|  | import "google/protobuf/empty.proto"; | ||||||
|  | import "github.com/docker/containerd/api/types/mount/mount.proto"; | ||||||
|  | import "github.com/docker/containerd/api/types/descriptor/descriptor.proto"; | ||||||
|  | 
 | ||||||
|  | service RootFS { | ||||||
|  | 	rpc Prepare(PrepareRequest) returns (PrepareResponse); | ||||||
|  | 
 | ||||||
|  | 	// TODO: Add method for initializing and retrieving mounts | ||||||
|  | 	//rpc InitMounts(InitRequest) returns (MountResponse); | ||||||
|  | 	//rpc Mounts(MountRequest) returns (MountResponse); | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | message PrepareRequest { | ||||||
|  | 	repeated containerd.v1.types.Descriptor layers = 1; | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | message PrepareResponse { | ||||||
|  | 	string chainid = 1 [(gogoproto.customtype) = "github.com/opencontainers/go-digest.Digest", (gogoproto.nullable) = false, (gogoproto.customname) = "ChainID"]; | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | //message InitRequest { | ||||||
|  | //	string name = 1; | ||||||
|  | //	string chainID = 2; | ||||||
|  | //	bool Readonly = 3; | ||||||
|  | //} | ||||||
|  | // | ||||||
|  | //message MountRequest { | ||||||
|  | //	string name = 1; | ||||||
|  | //} | ||||||
|  | // | ||||||
|  | //message MountResponse { | ||||||
|  | //	repeated containerd.v1.types.Mount mounts = 1; | ||||||
|  | //} | ||||||
							
								
								
									
										417
									
								
								api/types/descriptor/descriptor.pb.go
									
										
									
									
									
										Normal file
									
								
							
							
						
						
									
										417
									
								
								api/types/descriptor/descriptor.pb.go
									
										
									
									
									
										Normal file
									
								
							|  | @ -0,0 +1,417 @@ | ||||||
|  | // Code generated by protoc-gen-gogo. | ||||||
|  | // source: github.com/docker/containerd/api/types/descriptor/descriptor.proto | ||||||
|  | // DO NOT EDIT! | ||||||
|  | 
 | ||||||
|  | /* | ||||||
|  | 	Package descriptor is a generated protocol buffer package. | ||||||
|  | 
 | ||||||
|  | 	It is generated from these files: | ||||||
|  | 		github.com/docker/containerd/api/types/descriptor/descriptor.proto | ||||||
|  | 
 | ||||||
|  | 	It has these top-level messages: | ||||||
|  | 		Descriptor | ||||||
|  | */ | ||||||
|  | package descriptor | ||||||
|  | 
 | ||||||
|  | import proto "github.com/gogo/protobuf/proto" | ||||||
|  | import fmt "fmt" | ||||||
|  | import math "math" | ||||||
|  | import _ "github.com/gogo/protobuf/gogoproto" | ||||||
|  | 
 | ||||||
|  | import github_com_opencontainers_go_digest "github.com/opencontainers/go-digest" | ||||||
|  | 
 | ||||||
|  | import strings "strings" | ||||||
|  | import reflect "reflect" | ||||||
|  | 
 | ||||||
|  | import io "io" | ||||||
|  | 
 | ||||||
|  | // Reference imports to suppress errors if they are not otherwise used. | ||||||
|  | var _ = proto.Marshal | ||||||
|  | var _ = fmt.Errorf | ||||||
|  | var _ = math.Inf | ||||||
|  | 
 | ||||||
|  | // This is a compile-time assertion to ensure that this generated file | ||||||
|  | // is compatible with the proto package it is being compiled against. | ||||||
|  | // A compilation error at this line likely means your copy of the | ||||||
|  | // proto package needs to be updated. | ||||||
|  | const _ = proto.GoGoProtoPackageIsVersion2 // please upgrade the proto package | ||||||
|  | 
 | ||||||
|  | type Descriptor struct { | ||||||
|  | 	MediaType string                                     `protobuf:"bytes,1,opt,name=mediaType,proto3" json:"mediaType,omitempty"` | ||||||
|  | 	Digest    github_com_opencontainers_go_digest.Digest `protobuf:"bytes,2,opt,name=digest,proto3,customtype=github.com/opencontainers/go-digest.Digest" json:"digest"` | ||||||
|  | 	MediaSize int64                                      `protobuf:"varint,3,opt,name=mediaSize,proto3" json:"mediaSize,omitempty"` | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | func (m *Descriptor) Reset()                    { *m = Descriptor{} } | ||||||
|  | func (*Descriptor) ProtoMessage()               {} | ||||||
|  | func (*Descriptor) Descriptor() ([]byte, []int) { return fileDescriptorDescriptor, []int{0} } | ||||||
|  | 
 | ||||||
|  | func init() { | ||||||
|  | 	proto.RegisterType((*Descriptor)(nil), "containerd.v1.types.Descriptor") | ||||||
|  | } | ||||||
|  | func (m *Descriptor) Marshal() (dAtA []byte, err error) { | ||||||
|  | 	size := m.Size() | ||||||
|  | 	dAtA = make([]byte, size) | ||||||
|  | 	n, err := m.MarshalTo(dAtA) | ||||||
|  | 	if err != nil { | ||||||
|  | 		return nil, err | ||||||
|  | 	} | ||||||
|  | 	return dAtA[:n], nil | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | func (m *Descriptor) MarshalTo(dAtA []byte) (int, error) { | ||||||
|  | 	var i int | ||||||
|  | 	_ = i | ||||||
|  | 	var l int | ||||||
|  | 	_ = l | ||||||
|  | 	if len(m.MediaType) > 0 { | ||||||
|  | 		dAtA[i] = 0xa | ||||||
|  | 		i++ | ||||||
|  | 		i = encodeVarintDescriptor(dAtA, i, uint64(len(m.MediaType))) | ||||||
|  | 		i += copy(dAtA[i:], m.MediaType) | ||||||
|  | 	} | ||||||
|  | 	if len(m.Digest) > 0 { | ||||||
|  | 		dAtA[i] = 0x12 | ||||||
|  | 		i++ | ||||||
|  | 		i = encodeVarintDescriptor(dAtA, i, uint64(len(m.Digest))) | ||||||
|  | 		i += copy(dAtA[i:], m.Digest) | ||||||
|  | 	} | ||||||
|  | 	if m.MediaSize != 0 { | ||||||
|  | 		dAtA[i] = 0x18 | ||||||
|  | 		i++ | ||||||
|  | 		i = encodeVarintDescriptor(dAtA, i, uint64(m.MediaSize)) | ||||||
|  | 	} | ||||||
|  | 	return i, nil | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | func encodeFixed64Descriptor(dAtA []byte, offset int, v uint64) int { | ||||||
|  | 	dAtA[offset] = uint8(v) | ||||||
|  | 	dAtA[offset+1] = uint8(v >> 8) | ||||||
|  | 	dAtA[offset+2] = uint8(v >> 16) | ||||||
|  | 	dAtA[offset+3] = uint8(v >> 24) | ||||||
|  | 	dAtA[offset+4] = uint8(v >> 32) | ||||||
|  | 	dAtA[offset+5] = uint8(v >> 40) | ||||||
|  | 	dAtA[offset+6] = uint8(v >> 48) | ||||||
|  | 	dAtA[offset+7] = uint8(v >> 56) | ||||||
|  | 	return offset + 8 | ||||||
|  | } | ||||||
|  | func encodeFixed32Descriptor(dAtA []byte, offset int, v uint32) int { | ||||||
|  | 	dAtA[offset] = uint8(v) | ||||||
|  | 	dAtA[offset+1] = uint8(v >> 8) | ||||||
|  | 	dAtA[offset+2] = uint8(v >> 16) | ||||||
|  | 	dAtA[offset+3] = uint8(v >> 24) | ||||||
|  | 	return offset + 4 | ||||||
|  | } | ||||||
|  | func encodeVarintDescriptor(dAtA []byte, offset int, v uint64) int { | ||||||
|  | 	for v >= 1<<7 { | ||||||
|  | 		dAtA[offset] = uint8(v&0x7f | 0x80) | ||||||
|  | 		v >>= 7 | ||||||
|  | 		offset++ | ||||||
|  | 	} | ||||||
|  | 	dAtA[offset] = uint8(v) | ||||||
|  | 	return offset + 1 | ||||||
|  | } | ||||||
|  | func (m *Descriptor) Size() (n int) { | ||||||
|  | 	var l int | ||||||
|  | 	_ = l | ||||||
|  | 	l = len(m.MediaType) | ||||||
|  | 	if l > 0 { | ||||||
|  | 		n += 1 + l + sovDescriptor(uint64(l)) | ||||||
|  | 	} | ||||||
|  | 	l = len(m.Digest) | ||||||
|  | 	if l > 0 { | ||||||
|  | 		n += 1 + l + sovDescriptor(uint64(l)) | ||||||
|  | 	} | ||||||
|  | 	if m.MediaSize != 0 { | ||||||
|  | 		n += 1 + sovDescriptor(uint64(m.MediaSize)) | ||||||
|  | 	} | ||||||
|  | 	return n | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | func sovDescriptor(x uint64) (n int) { | ||||||
|  | 	for { | ||||||
|  | 		n++ | ||||||
|  | 		x >>= 7 | ||||||
|  | 		if x == 0 { | ||||||
|  | 			break | ||||||
|  | 		} | ||||||
|  | 	} | ||||||
|  | 	return n | ||||||
|  | } | ||||||
|  | func sozDescriptor(x uint64) (n int) { | ||||||
|  | 	return sovDescriptor(uint64((x << 1) ^ uint64((int64(x) >> 63)))) | ||||||
|  | } | ||||||
|  | func (this *Descriptor) String() string { | ||||||
|  | 	if this == nil { | ||||||
|  | 		return "nil" | ||||||
|  | 	} | ||||||
|  | 	s := strings.Join([]string{`&Descriptor{`, | ||||||
|  | 		`MediaType:` + fmt.Sprintf("%v", this.MediaType) + `,`, | ||||||
|  | 		`Digest:` + fmt.Sprintf("%v", this.Digest) + `,`, | ||||||
|  | 		`MediaSize:` + fmt.Sprintf("%v", this.MediaSize) + `,`, | ||||||
|  | 		`}`, | ||||||
|  | 	}, "") | ||||||
|  | 	return s | ||||||
|  | } | ||||||
|  | func valueToStringDescriptor(v interface{}) string { | ||||||
|  | 	rv := reflect.ValueOf(v) | ||||||
|  | 	if rv.IsNil() { | ||||||
|  | 		return "nil" | ||||||
|  | 	} | ||||||
|  | 	pv := reflect.Indirect(rv).Interface() | ||||||
|  | 	return fmt.Sprintf("*%v", pv) | ||||||
|  | } | ||||||
|  | func (m *Descriptor) Unmarshal(dAtA []byte) error { | ||||||
|  | 	l := len(dAtA) | ||||||
|  | 	iNdEx := 0 | ||||||
|  | 	for iNdEx < l { | ||||||
|  | 		preIndex := iNdEx | ||||||
|  | 		var wire uint64 | ||||||
|  | 		for shift := uint(0); ; shift += 7 { | ||||||
|  | 			if shift >= 64 { | ||||||
|  | 				return ErrIntOverflowDescriptor | ||||||
|  | 			} | ||||||
|  | 			if iNdEx >= l { | ||||||
|  | 				return io.ErrUnexpectedEOF | ||||||
|  | 			} | ||||||
|  | 			b := dAtA[iNdEx] | ||||||
|  | 			iNdEx++ | ||||||
|  | 			wire |= (uint64(b) & 0x7F) << shift | ||||||
|  | 			if b < 0x80 { | ||||||
|  | 				break | ||||||
|  | 			} | ||||||
|  | 		} | ||||||
|  | 		fieldNum := int32(wire >> 3) | ||||||
|  | 		wireType := int(wire & 0x7) | ||||||
|  | 		if wireType == 4 { | ||||||
|  | 			return fmt.Errorf("proto: Descriptor: wiretype end group for non-group") | ||||||
|  | 		} | ||||||
|  | 		if fieldNum <= 0 { | ||||||
|  | 			return fmt.Errorf("proto: Descriptor: illegal tag %d (wire type %d)", fieldNum, wire) | ||||||
|  | 		} | ||||||
|  | 		switch fieldNum { | ||||||
|  | 		case 1: | ||||||
|  | 			if wireType != 2 { | ||||||
|  | 				return fmt.Errorf("proto: wrong wireType = %d for field MediaType", wireType) | ||||||
|  | 			} | ||||||
|  | 			var stringLen uint64 | ||||||
|  | 			for shift := uint(0); ; shift += 7 { | ||||||
|  | 				if shift >= 64 { | ||||||
|  | 					return ErrIntOverflowDescriptor | ||||||
|  | 				} | ||||||
|  | 				if iNdEx >= l { | ||||||
|  | 					return io.ErrUnexpectedEOF | ||||||
|  | 				} | ||||||
|  | 				b := dAtA[iNdEx] | ||||||
|  | 				iNdEx++ | ||||||
|  | 				stringLen |= (uint64(b) & 0x7F) << shift | ||||||
|  | 				if b < 0x80 { | ||||||
|  | 					break | ||||||
|  | 				} | ||||||
|  | 			} | ||||||
|  | 			intStringLen := int(stringLen) | ||||||
|  | 			if intStringLen < 0 { | ||||||
|  | 				return ErrInvalidLengthDescriptor | ||||||
|  | 			} | ||||||
|  | 			postIndex := iNdEx + intStringLen | ||||||
|  | 			if postIndex > l { | ||||||
|  | 				return io.ErrUnexpectedEOF | ||||||
|  | 			} | ||||||
|  | 			m.MediaType = string(dAtA[iNdEx:postIndex]) | ||||||
|  | 			iNdEx = postIndex | ||||||
|  | 		case 2: | ||||||
|  | 			if wireType != 2 { | ||||||
|  | 				return fmt.Errorf("proto: wrong wireType = %d for field Digest", wireType) | ||||||
|  | 			} | ||||||
|  | 			var stringLen uint64 | ||||||
|  | 			for shift := uint(0); ; shift += 7 { | ||||||
|  | 				if shift >= 64 { | ||||||
|  | 					return ErrIntOverflowDescriptor | ||||||
|  | 				} | ||||||
|  | 				if iNdEx >= l { | ||||||
|  | 					return io.ErrUnexpectedEOF | ||||||
|  | 				} | ||||||
|  | 				b := dAtA[iNdEx] | ||||||
|  | 				iNdEx++ | ||||||
|  | 				stringLen |= (uint64(b) & 0x7F) << shift | ||||||
|  | 				if b < 0x80 { | ||||||
|  | 					break | ||||||
|  | 				} | ||||||
|  | 			} | ||||||
|  | 			intStringLen := int(stringLen) | ||||||
|  | 			if intStringLen < 0 { | ||||||
|  | 				return ErrInvalidLengthDescriptor | ||||||
|  | 			} | ||||||
|  | 			postIndex := iNdEx + intStringLen | ||||||
|  | 			if postIndex > l { | ||||||
|  | 				return io.ErrUnexpectedEOF | ||||||
|  | 			} | ||||||
|  | 			m.Digest = github_com_opencontainers_go_digest.Digest(dAtA[iNdEx:postIndex]) | ||||||
|  | 			iNdEx = postIndex | ||||||
|  | 		case 3: | ||||||
|  | 			if wireType != 0 { | ||||||
|  | 				return fmt.Errorf("proto: wrong wireType = %d for field MediaSize", wireType) | ||||||
|  | 			} | ||||||
|  | 			m.MediaSize = 0 | ||||||
|  | 			for shift := uint(0); ; shift += 7 { | ||||||
|  | 				if shift >= 64 { | ||||||
|  | 					return ErrIntOverflowDescriptor | ||||||
|  | 				} | ||||||
|  | 				if iNdEx >= l { | ||||||
|  | 					return io.ErrUnexpectedEOF | ||||||
|  | 				} | ||||||
|  | 				b := dAtA[iNdEx] | ||||||
|  | 				iNdEx++ | ||||||
|  | 				m.MediaSize |= (int64(b) & 0x7F) << shift | ||||||
|  | 				if b < 0x80 { | ||||||
|  | 					break | ||||||
|  | 				} | ||||||
|  | 			} | ||||||
|  | 		default: | ||||||
|  | 			iNdEx = preIndex | ||||||
|  | 			skippy, err := skipDescriptor(dAtA[iNdEx:]) | ||||||
|  | 			if err != nil { | ||||||
|  | 				return err | ||||||
|  | 			} | ||||||
|  | 			if skippy < 0 { | ||||||
|  | 				return ErrInvalidLengthDescriptor | ||||||
|  | 			} | ||||||
|  | 			if (iNdEx + skippy) > l { | ||||||
|  | 				return io.ErrUnexpectedEOF | ||||||
|  | 			} | ||||||
|  | 			iNdEx += skippy | ||||||
|  | 		} | ||||||
|  | 	} | ||||||
|  | 
 | ||||||
|  | 	if iNdEx > l { | ||||||
|  | 		return io.ErrUnexpectedEOF | ||||||
|  | 	} | ||||||
|  | 	return nil | ||||||
|  | } | ||||||
|  | func skipDescriptor(dAtA []byte) (n int, err error) { | ||||||
|  | 	l := len(dAtA) | ||||||
|  | 	iNdEx := 0 | ||||||
|  | 	for iNdEx < l { | ||||||
|  | 		var wire uint64 | ||||||
|  | 		for shift := uint(0); ; shift += 7 { | ||||||
|  | 			if shift >= 64 { | ||||||
|  | 				return 0, ErrIntOverflowDescriptor | ||||||
|  | 			} | ||||||
|  | 			if iNdEx >= l { | ||||||
|  | 				return 0, io.ErrUnexpectedEOF | ||||||
|  | 			} | ||||||
|  | 			b := dAtA[iNdEx] | ||||||
|  | 			iNdEx++ | ||||||
|  | 			wire |= (uint64(b) & 0x7F) << shift | ||||||
|  | 			if b < 0x80 { | ||||||
|  | 				break | ||||||
|  | 			} | ||||||
|  | 		} | ||||||
|  | 		wireType := int(wire & 0x7) | ||||||
|  | 		switch wireType { | ||||||
|  | 		case 0: | ||||||
|  | 			for shift := uint(0); ; shift += 7 { | ||||||
|  | 				if shift >= 64 { | ||||||
|  | 					return 0, ErrIntOverflowDescriptor | ||||||
|  | 				} | ||||||
|  | 				if iNdEx >= l { | ||||||
|  | 					return 0, io.ErrUnexpectedEOF | ||||||
|  | 				} | ||||||
|  | 				iNdEx++ | ||||||
|  | 				if dAtA[iNdEx-1] < 0x80 { | ||||||
|  | 					break | ||||||
|  | 				} | ||||||
|  | 			} | ||||||
|  | 			return iNdEx, nil | ||||||
|  | 		case 1: | ||||||
|  | 			iNdEx += 8 | ||||||
|  | 			return iNdEx, nil | ||||||
|  | 		case 2: | ||||||
|  | 			var length int | ||||||
|  | 			for shift := uint(0); ; shift += 7 { | ||||||
|  | 				if shift >= 64 { | ||||||
|  | 					return 0, ErrIntOverflowDescriptor | ||||||
|  | 				} | ||||||
|  | 				if iNdEx >= l { | ||||||
|  | 					return 0, io.ErrUnexpectedEOF | ||||||
|  | 				} | ||||||
|  | 				b := dAtA[iNdEx] | ||||||
|  | 				iNdEx++ | ||||||
|  | 				length |= (int(b) & 0x7F) << shift | ||||||
|  | 				if b < 0x80 { | ||||||
|  | 					break | ||||||
|  | 				} | ||||||
|  | 			} | ||||||
|  | 			iNdEx += length | ||||||
|  | 			if length < 0 { | ||||||
|  | 				return 0, ErrInvalidLengthDescriptor | ||||||
|  | 			} | ||||||
|  | 			return iNdEx, nil | ||||||
|  | 		case 3: | ||||||
|  | 			for { | ||||||
|  | 				var innerWire uint64 | ||||||
|  | 				var start int = iNdEx | ||||||
|  | 				for shift := uint(0); ; shift += 7 { | ||||||
|  | 					if shift >= 64 { | ||||||
|  | 						return 0, ErrIntOverflowDescriptor | ||||||
|  | 					} | ||||||
|  | 					if iNdEx >= l { | ||||||
|  | 						return 0, io.ErrUnexpectedEOF | ||||||
|  | 					} | ||||||
|  | 					b := dAtA[iNdEx] | ||||||
|  | 					iNdEx++ | ||||||
|  | 					innerWire |= (uint64(b) & 0x7F) << shift | ||||||
|  | 					if b < 0x80 { | ||||||
|  | 						break | ||||||
|  | 					} | ||||||
|  | 				} | ||||||
|  | 				innerWireType := int(innerWire & 0x7) | ||||||
|  | 				if innerWireType == 4 { | ||||||
|  | 					break | ||||||
|  | 				} | ||||||
|  | 				next, err := skipDescriptor(dAtA[start:]) | ||||||
|  | 				if err != nil { | ||||||
|  | 					return 0, err | ||||||
|  | 				} | ||||||
|  | 				iNdEx = start + next | ||||||
|  | 			} | ||||||
|  | 			return iNdEx, nil | ||||||
|  | 		case 4: | ||||||
|  | 			return iNdEx, nil | ||||||
|  | 		case 5: | ||||||
|  | 			iNdEx += 4 | ||||||
|  | 			return iNdEx, nil | ||||||
|  | 		default: | ||||||
|  | 			return 0, fmt.Errorf("proto: illegal wireType %d", wireType) | ||||||
|  | 		} | ||||||
|  | 	} | ||||||
|  | 	panic("unreachable") | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | var ( | ||||||
|  | 	ErrInvalidLengthDescriptor = fmt.Errorf("proto: negative length found during unmarshaling") | ||||||
|  | 	ErrIntOverflowDescriptor   = fmt.Errorf("proto: integer overflow") | ||||||
|  | ) | ||||||
|  | 
 | ||||||
|  | func init() { | ||||||
|  | 	proto.RegisterFile("github.com/docker/containerd/api/types/descriptor/descriptor.proto", fileDescriptorDescriptor) | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | var fileDescriptorDescriptor = []byte{ | ||||||
|  | 	// 230 bytes of a gzipped FileDescriptorProto | ||||||
|  | 	0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xe2, 0x72, 0x4a, 0xcf, 0x2c, 0xc9, | ||||||
|  | 	0x28, 0x4d, 0xd2, 0x4b, 0xce, 0xcf, 0xd5, 0x4f, 0xc9, 0x4f, 0xce, 0x4e, 0x2d, 0xd2, 0x4f, 0xce, | ||||||
|  | 	0xcf, 0x2b, 0x49, 0xcc, 0xcc, 0x4b, 0x2d, 0x4a, 0xd1, 0x4f, 0x2c, 0xc8, 0xd4, 0x2f, 0xa9, 0x2c, | ||||||
|  | 	0x48, 0x2d, 0xd6, 0x4f, 0x49, 0x2d, 0x4e, 0x2e, 0xca, 0x2c, 0x28, 0xc9, 0x2f, 0x42, 0x62, 0xea, | ||||||
|  | 	0x15, 0x14, 0xe5, 0x97, 0xe4, 0x0b, 0x09, 0x23, 0x74, 0xe8, 0x95, 0x19, 0xea, 0x81, 0x35, 0x48, | ||||||
|  | 	0x89, 0xa4, 0xe7, 0xa7, 0xe7, 0x83, 0xe5, 0xf5, 0x41, 0x2c, 0x88, 0x52, 0xa5, 0x29, 0x8c, 0x5c, | ||||||
|  | 	0x5c, 0x2e, 0x70, 0xfd, 0x42, 0x32, 0x5c, 0x9c, 0xb9, 0xa9, 0x29, 0x99, 0x89, 0x21, 0x95, 0x05, | ||||||
|  | 	0xa9, 0x12, 0x8c, 0x0a, 0x8c, 0x1a, 0x9c, 0x41, 0x08, 0x01, 0x21, 0x2f, 0x2e, 0xb6, 0x94, 0xcc, | ||||||
|  | 	0xf4, 0xd4, 0xe2, 0x12, 0x09, 0x26, 0x90, 0x94, 0x93, 0xd1, 0x89, 0x7b, 0xf2, 0x0c, 0xb7, 0xee, | ||||||
|  | 	0xc9, 0x6b, 0x21, 0xb9, 0x39, 0xbf, 0x20, 0x35, 0x0f, 0x6e, 0x7d, 0xb1, 0x7e, 0x7a, 0xbe, 0x2e, | ||||||
|  | 	0x44, 0x8b, 0x9e, 0x0b, 0x98, 0x0a, 0x82, 0x9a, 0x00, 0xb7, 0x29, 0x38, 0xb3, 0x2a, 0x55, 0x82, | ||||||
|  | 	0x59, 0x81, 0x51, 0x83, 0x39, 0x08, 0x21, 0xe0, 0x24, 0x71, 0xe2, 0xa1, 0x1c, 0xc3, 0x8d, 0x87, | ||||||
|  | 	0x72, 0x0c, 0x0d, 0x8f, 0xe4, 0x18, 0x4f, 0x3c, 0x92, 0x63, 0xbc, 0xf0, 0x48, 0x8e, 0xf1, 0xc1, | ||||||
|  | 	0x23, 0x39, 0xc6, 0x24, 0x36, 0xb0, 0xbb, 0x8d, 0x01, 0x01, 0x00, 0x00, 0xff, 0xff, 0xf2, 0x3c, | ||||||
|  | 	0x86, 0x2d, 0x28, 0x01, 0x00, 0x00, | ||||||
|  | } | ||||||
							
								
								
									
										11
									
								
								api/types/descriptor/descriptor.proto
									
										
									
									
									
										Normal file
									
								
							
							
						
						
									
										11
									
								
								api/types/descriptor/descriptor.proto
									
										
									
									
									
										Normal file
									
								
							|  | @ -0,0 +1,11 @@ | ||||||
|  | syntax = "proto3"; | ||||||
|  | 
 | ||||||
|  | package containerd.v1.types; | ||||||
|  | 
 | ||||||
|  | import "gogoproto/gogo.proto"; | ||||||
|  | 
 | ||||||
|  | message Descriptor { | ||||||
|  | 	string mediaType = 1; | ||||||
|  | 	string digest = 2 [(gogoproto.customtype) = "github.com/opencontainers/go-digest.Digest", (gogoproto.nullable) = false]; | ||||||
|  | 	int64 mediaSize = 3; | ||||||
|  | } | ||||||
|  | @ -7,6 +7,7 @@ import ( | ||||||
| 	_ "github.com/docker/containerd/services/execution" | 	_ "github.com/docker/containerd/services/execution" | ||||||
| 	_ "github.com/docker/containerd/services/healthcheck" | 	_ "github.com/docker/containerd/services/healthcheck" | ||||||
| 	_ "github.com/docker/containerd/services/metrics" | 	_ "github.com/docker/containerd/services/metrics" | ||||||
|  | 	_ "github.com/docker/containerd/services/rootfs" | ||||||
| 	_ "github.com/docker/containerd/snapshot/btrfs" | 	_ "github.com/docker/containerd/snapshot/btrfs" | ||||||
| 	_ "github.com/docker/containerd/snapshot/overlay" | 	_ "github.com/docker/containerd/snapshot/overlay" | ||||||
| ) | ) | ||||||
|  |  | ||||||
|  | @ -16,9 +16,13 @@ import ( | ||||||
| 	"github.com/pkg/errors" | 	"github.com/pkg/errors" | ||||||
| ) | ) | ||||||
| 
 | 
 | ||||||
|  | type Preparer interface { | ||||||
|  | 	Prepare(ctx context.Context, layers []ocispec.Descriptor) (digest.Digest, error) | ||||||
|  | } | ||||||
|  | 
 | ||||||
| type Mounter interface { | type Mounter interface { | ||||||
| 	Mount(mounts ...containerd.Mount) error | 	Mount(target string, mounts ...containerd.Mount) error | ||||||
| 	Unmount(mounts ...containerd.Mount) error | 	Unmount(target string) error | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| // ApplyLayer applies the layer to the provided parent. The resulting snapshot | // ApplyLayer applies the layer to the provided parent. The resulting snapshot | ||||||
|  | @ -51,13 +55,13 @@ func ApplyLayer(snapshots snapshot.Snapshotter, mounter Mounter, rd io.Reader, p | ||||||
| 		return "", err | 		return "", err | ||||||
| 	} | 	} | ||||||
| 
 | 
 | ||||||
| 	if err := mounter.Mount(mounts...); err != nil { | 	if err := mounter.Mount(dir, mounts...); err != nil { | ||||||
| 		if err := snapshots.Remove(ctx, key); err != nil { | 		if err := snapshots.Remove(ctx, key); err != nil { | ||||||
| 			log.L.WithError(err).Error("snapshot rollback failed") | 			log.L.WithError(err).Error("snapshot rollback failed") | ||||||
| 		} | 		} | ||||||
| 		return "", err | 		return "", err | ||||||
| 	} | 	} | ||||||
| 	defer mounter.Unmount(mounts...) | 	defer mounter.Unmount(dir) | ||||||
| 
 | 
 | ||||||
| 	rd, err = dockerarchive.DecompressStream(rd) | 	rd, err = dockerarchive.DecompressStream(rd) | ||||||
| 	if err != nil { | 	if err != nil { | ||||||
|  | @ -74,6 +78,9 @@ func ApplyLayer(snapshots snapshot.Snapshotter, mounter Mounter, rd io.Reader, p | ||||||
| 	if parent != "" { | 	if parent != "" { | ||||||
| 		chainID = identity.ChainID([]digest.Digest{parent, chainID}) | 		chainID = identity.ChainID([]digest.Digest{parent, chainID}) | ||||||
| 	} | 	} | ||||||
|  | 	if _, err := snapshots.Stat(ctx, chainID.String()); err == nil { | ||||||
|  | 		return diffID, nil //TODO: call snapshots.Remove(ctx, key) once implemented | ||||||
|  | 	} | ||||||
| 
 | 
 | ||||||
| 	return diffID, snapshots.Commit(ctx, chainID.String(), key) | 	return diffID, snapshots.Commit(ctx, chainID.String(), key) | ||||||
| } | } | ||||||
|  | @ -90,7 +97,7 @@ func Prepare(ctx context.Context, snapshots snapshot.Snapshotter, mounter Mounte | ||||||
| 	// rootfs Controller. | 	// rootfs Controller. | ||||||
| 	// | 	// | ||||||
| 	// Just pass them in for now. | 	// Just pass them in for now. | ||||||
| 	openBlob func(digest.Digest) (io.ReadCloser, error), | 	openBlob func(context.Context, digest.Digest) (io.ReadCloser, error), | ||||||
| 	resolveDiffID func(digest.Digest) digest.Digest, | 	resolveDiffID func(digest.Digest) digest.Digest, | ||||||
| 	registerDiffID func(diffID, dgst digest.Digest) error) (digest.Digest, error) { | 	registerDiffID func(diffID, dgst digest.Digest) error) (digest.Digest, error) { | ||||||
| 	var ( | 	var ( | ||||||
|  | @ -116,7 +123,7 @@ func Prepare(ctx context.Context, snapshots snapshot.Snapshotter, mounter Mounte | ||||||
| 			} | 			} | ||||||
| 		} | 		} | ||||||
| 
 | 
 | ||||||
| 		rc, err := openBlob(layerDigest) | 		rc, err := openBlob(ctx, layerDigest) | ||||||
| 		if err != nil { | 		if err != nil { | ||||||
| 			return "", err | 			return "", err | ||||||
| 		} | 		} | ||||||
|  |  | ||||||
							
								
								
									
										39
									
								
								services/rootfs/preparer.go
									
										
									
									
									
										Normal file
									
								
							
							
						
						
									
										39
									
								
								services/rootfs/preparer.go
									
										
									
									
									
										Normal file
									
								
							|  | @ -0,0 +1,39 @@ | ||||||
|  | package rootfs | ||||||
|  | 
 | ||||||
|  | import ( | ||||||
|  | 	"context" | ||||||
|  | 
 | ||||||
|  | 	rootfsapi "github.com/docker/containerd/api/services/rootfs" | ||||||
|  | 	containerd_v1_types "github.com/docker/containerd/api/types/descriptor" | ||||||
|  | 	"github.com/docker/containerd/rootfs" | ||||||
|  | 	digest "github.com/opencontainers/go-digest" | ||||||
|  | 	ocispec "github.com/opencontainers/image-spec/specs-go/v1" | ||||||
|  | ) | ||||||
|  | 
 | ||||||
|  | func NewPreparerFromClient(client rootfsapi.RootFSClient) rootfs.Preparer { | ||||||
|  | 	return remotePreparer{ | ||||||
|  | 		client: client, | ||||||
|  | 	} | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | type remotePreparer struct { | ||||||
|  | 	client rootfsapi.RootFSClient | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | func (rp remotePreparer) Prepare(ctx context.Context, layers []ocispec.Descriptor) (digest.Digest, error) { | ||||||
|  | 	pr := rootfsapi.PrepareRequest{ | ||||||
|  | 		Layers: make([]*containerd_v1_types.Descriptor, len(layers)), | ||||||
|  | 	} | ||||||
|  | 	for i, l := range layers { | ||||||
|  | 		pr.Layers[i] = &containerd_v1_types.Descriptor{ | ||||||
|  | 			MediaType: l.MediaType, | ||||||
|  | 			Digest:    l.Digest, | ||||||
|  | 			MediaSize: l.Size, | ||||||
|  | 		} | ||||||
|  | 	} | ||||||
|  | 	resp, err := rp.client.Prepare(ctx, &pr) | ||||||
|  | 	if err != nil { | ||||||
|  | 		return "", nil | ||||||
|  | 	} | ||||||
|  | 	return resp.ChainID, nil | ||||||
|  | } | ||||||
							
								
								
									
										86
									
								
								services/rootfs/service.go
									
										
									
									
									
										Normal file
									
								
							
							
						
						
									
										86
									
								
								services/rootfs/service.go
									
										
									
									
									
										Normal file
									
								
							|  | @ -0,0 +1,86 @@ | ||||||
|  | package rootfs | ||||||
|  | 
 | ||||||
|  | import ( | ||||||
|  | 	"syscall" | ||||||
|  | 
 | ||||||
|  | 	"github.com/docker/containerd" | ||||||
|  | 	rootfsapi "github.com/docker/containerd/api/services/rootfs" | ||||||
|  | 	"github.com/docker/containerd/content" | ||||||
|  | 	"github.com/docker/containerd/log" | ||||||
|  | 	"github.com/docker/containerd/plugin" | ||||||
|  | 	"github.com/docker/containerd/rootfs" | ||||||
|  | 	"github.com/docker/containerd/snapshot" | ||||||
|  | 	digest "github.com/opencontainers/go-digest" | ||||||
|  | 	ocispec "github.com/opencontainers/image-spec/specs-go/v1" | ||||||
|  | 	"golang.org/x/net/context" | ||||||
|  | 	"google.golang.org/grpc" | ||||||
|  | ) | ||||||
|  | 
 | ||||||
|  | func init() { | ||||||
|  | 	plugin.Register("rootfs-grpc", &plugin.Registration{ | ||||||
|  | 		Type: plugin.GRPCPlugin, | ||||||
|  | 		Init: func(ic *plugin.InitContext) (interface{}, error) { | ||||||
|  | 			return NewService(ic.Store, ic.Snapshotter) | ||||||
|  | 		}, | ||||||
|  | 	}) | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | type Service struct { | ||||||
|  | 	store       *content.Store | ||||||
|  | 	snapshotter snapshot.Snapshotter | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | func NewService(store *content.Store, snapshotter snapshot.Snapshotter) (*Service, error) { | ||||||
|  | 	return &Service{ | ||||||
|  | 		store:       store, | ||||||
|  | 		snapshotter: snapshotter, | ||||||
|  | 	}, nil | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | func (s *Service) Register(gs *grpc.Server) error { | ||||||
|  | 	rootfsapi.RegisterRootFSServer(gs, s) | ||||||
|  | 	return nil | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | func (s *Service) Prepare(ctx context.Context, pr *rootfsapi.PrepareRequest) (*rootfsapi.PrepareResponse, error) { | ||||||
|  | 	layers := make([]ocispec.Descriptor, len(pr.Layers)) | ||||||
|  | 	for i, l := range pr.Layers { | ||||||
|  | 		layers[i] = ocispec.Descriptor{ | ||||||
|  | 			MediaType: l.MediaType, | ||||||
|  | 			Digest:    l.Digest, | ||||||
|  | 			Size:      l.MediaSize, | ||||||
|  | 		} | ||||||
|  | 	} | ||||||
|  | 	log.G(ctx).Infof("Preparing %#v", layers) | ||||||
|  | 	chainID, err := rootfs.Prepare(ctx, s.snapshotter, mounter{}, layers, s.store.Reader, emptyResolver, noopRegister) | ||||||
|  | 	if err != nil { | ||||||
|  | 		log.G(ctx).Errorf("Rootfs Prepare failed!: %v", err) | ||||||
|  | 		return nil, err | ||||||
|  | 	} | ||||||
|  | 	log.G(ctx).Infof("ChainID %#v", chainID) | ||||||
|  | 	return &rootfsapi.PrepareResponse{ | ||||||
|  | 		ChainID: chainID, | ||||||
|  | 	}, nil | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | type mounter struct{} | ||||||
|  | 
 | ||||||
|  | func (mounter) Mount(dir string, mounts ...containerd.Mount) error { | ||||||
|  | 	return containerd.MountAll(mounts, dir) | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | func (mounter) Unmount(dir string) error { | ||||||
|  | 	return syscall.Unmount(dir, 0) | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | func emptyResolver(digest.Digest) digest.Digest { | ||||||
|  | 	return digest.Digest("") | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | func noopRegister(digest.Digest, digest.Digest) error { | ||||||
|  | 	return nil | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | //func (s *Service) Mounts(ctx context.Context, mr *rootfsapi.MountRequest) (*rootfsapi.MountResponse, error) { | ||||||
|  | // | ||||||
|  | //} | ||||||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue