Ejemplo n.º 1
0
// MakeOIDBytes makes an OID encapsulating a byte slice. Note that it does not
// duplicate the data, but rather it points to it directly.
func (lib *Lib) MakeOIDBytes(data []byte) (*OID, error) {
	oid := lib.NewOID()

	s := C.malloc(C.gss_OID_size) // s for struct
	if s == nil {
		return nil, ErrMallocFailed
	}
	C.memset(s, 0, C.gss_OID_size)

	l := C.size_t(len(data))
	e := C.malloc(l) // c for contents
	if e == nil {
		return nil, ErrMallocFailed
	}
	C.memmove(e, (unsafe.Pointer)(&data[0]), l)

	oid.C_gss_OID = C.gss_OID(s)
	oid.alloc = allocMalloc

	// because of the alignment issues I can't access o.oid's fields from go,
	// so invoking a C function to do the same as:
	// oid.C_gss_OID.length = l
	// oid.C_gss_OID.elements = c
	C.helper_gss_OID_desc_set_elements(oid.C_gss_OID, C.OM_uint32(l), e)

	return oid, nil
}
Ejemplo n.º 2
0
// InitSecContext initiates a security context. Usually invoked by the client.
// A Context (CtxId) describes the state at one end of an authentication
// protocol. May return ErrContinueNeeded if the client is to make another
// iteration of exchanging token with the service
func (lib *Lib) InitSecContext(initiatorCredHandle *CredId, ctxIn *CtxId,
	targetName *Name, mechType *OID, reqFlags uint32, timeReq time.Duration,
	inputChanBindings ChannelBindings, inputToken *Buffer) (
	ctxOut *CtxId, actualMechType *OID, outputToken *Buffer, retFlags uint32,
	timeRec time.Duration, err error) {

	runtime.LockOSThread()
	defer runtime.UnlockOSThread()

	// prepare the input params
	C_initiator := C.gss_cred_id_t(nil)
	if initiatorCredHandle != nil {
		C_initiator = initiatorCredHandle.C_gss_cred_id_t
	}

	C_mechType := C.gss_OID(nil)
	if mechType != nil {
		C_mechType = mechType.C_gss_OID
	}

	C_inputToken := C.gss_buffer_t(nil)
	if inputToken != nil {
		C_inputToken = inputToken.C_gss_buffer_t
	}

	// prepare the outputs.
	if ctxIn != nil {
		ctxCopy := *ctxIn
		ctxOut = &ctxCopy
	} else {
		ctxOut = lib.NewCtxId()
	}

	min := C.OM_uint32(0)
	actualMechType = lib.NewOID()
	outputToken, err = lib.MakeBuffer(allocGSSAPI)
	if err != nil {
		return nil, nil, nil, 0, 0, err
	}

	flags := C.OM_uint32(0)
	timerec := C.OM_uint32(0)

	maj := C.wrap_gss_init_sec_context(lib.Fp_gss_init_sec_context,
		&min,
		C_initiator,
		&ctxOut.C_gss_ctx_id_t, // used as both in and out param
		targetName.C_gss_name_t,
		C_mechType,
		C.OM_uint32(reqFlags),
		C.OM_uint32(timeReq.Seconds()),
		C.gss_channel_bindings_t(inputChanBindings),
		C_inputToken,
		&actualMechType.C_gss_OID,
		outputToken.C_gss_buffer_t,
		&flags,
		&timerec)

	err = lib.stashLastStatus(maj, min)
	if err != nil {
		return nil, nil, nil, 0, 0, err
	}

	if MajorStatus(maj).ContinueNeeded() {
		err = ErrContinueNeeded
	}

	return ctxOut, actualMechType, outputToken,
		uint32(flags), time.Duration(timerec) * time.Second,
		err
}