package pgtype

import (
	
	
	
	
	
	
	
	
)

// PostgreSQL oids for common types
const (
	BoolOID                = 16
	ByteaOID               = 17
	QCharOID               = 18
	NameOID                = 19
	Int8OID                = 20
	Int2OID                = 21
	Int4OID                = 23
	TextOID                = 25
	OIDOID                 = 26
	TIDOID                 = 27
	XIDOID                 = 28
	CIDOID                 = 29
	JSONOID                = 114
	JSONArrayOID           = 199
	PointOID               = 600
	LsegOID                = 601
	PathOID                = 602
	BoxOID                 = 603
	PolygonOID             = 604
	LineOID                = 628
	LineArrayOID           = 629
	CIDROID                = 650
	CIDRArrayOID           = 651
	Float4OID              = 700
	Float8OID              = 701
	CircleOID              = 718
	CircleArrayOID         = 719
	UnknownOID             = 705
	MacaddrOID             = 829
	InetOID                = 869
	BoolArrayOID           = 1000
	QCharArrayOID          = 1002
	NameArrayOID           = 1003
	Int2ArrayOID           = 1005
	Int4ArrayOID           = 1007
	TextArrayOID           = 1009
	TIDArrayOID            = 1010
	ByteaArrayOID          = 1001
	XIDArrayOID            = 1011
	CIDArrayOID            = 1012
	BPCharArrayOID         = 1014
	VarcharArrayOID        = 1015
	Int8ArrayOID           = 1016
	PointArrayOID          = 1017
	LsegArrayOID           = 1018
	PathArrayOID           = 1019
	BoxArrayOID            = 1020
	Float4ArrayOID         = 1021
	Float8ArrayOID         = 1022
	PolygonArrayOID        = 1027
	OIDArrayOID            = 1028
	ACLItemOID             = 1033
	ACLItemArrayOID        = 1034
	MacaddrArrayOID        = 1040
	InetArrayOID           = 1041
	BPCharOID              = 1042
	VarcharOID             = 1043
	DateOID                = 1082
	TimeOID                = 1083
	TimestampOID           = 1114
	TimestampArrayOID      = 1115
	DateArrayOID           = 1182
	TimeArrayOID           = 1183
	TimestamptzOID         = 1184
	TimestamptzArrayOID    = 1185
	IntervalOID            = 1186
	IntervalArrayOID       = 1187
	NumericArrayOID        = 1231
	BitOID                 = 1560
	BitArrayOID            = 1561
	VarbitOID              = 1562
	VarbitArrayOID         = 1563
	NumericOID             = 1700
	RecordOID              = 2249
	RecordArrayOID         = 2287
	UUIDOID                = 2950
	UUIDArrayOID           = 2951
	JSONBOID               = 3802
	JSONBArrayOID          = 3807
	DaterangeOID           = 3912
	DaterangeArrayOID      = 3913
	Int4rangeOID           = 3904
	Int4rangeArrayOID      = 3905
	NumrangeOID            = 3906
	NumrangeArrayOID       = 3907
	TsrangeOID             = 3908
	TsrangeArrayOID        = 3909
	TstzrangeOID           = 3910
	TstzrangeArrayOID      = 3911
	Int8rangeOID           = 3926
	Int8rangeArrayOID      = 3927
	JSONPathOID            = 4072
	JSONPathArrayOID       = 4073
	Int4multirangeOID      = 4451
	NummultirangeOID       = 4532
	TsmultirangeOID        = 4533
	TstzmultirangeOID      = 4534
	DatemultirangeOID      = 4535
	Int8multirangeOID      = 4536
	Int4multirangeArrayOID = 6150
	NummultirangeArrayOID  = 6151
	TsmultirangeArrayOID   = 6152
	TstzmultirangeArrayOID = 6153
	DatemultirangeArrayOID = 6155
	Int8multirangeArrayOID = 6157
)

type InfinityModifier int8

const (
	Infinity         InfinityModifier = 1
	Finite           InfinityModifier = 0
	NegativeInfinity InfinityModifier = -Infinity
)

func ( InfinityModifier) () string {
	switch  {
	case Finite:
		return "finite"
	case Infinity:
		return "infinity"
	case NegativeInfinity:
		return "-infinity"
	default:
		return "invalid"
	}
}

// PostgreSQL format codes
const (
	TextFormatCode   = 0
	BinaryFormatCode = 1
)

// A Codec converts between Go and PostgreSQL values. A Codec must not be mutated after it is registered with a Map.
type Codec interface {
	// FormatSupported returns true if the format is supported.
	FormatSupported(int16) bool

	// PreferredFormat returns the preferred format.
	PreferredFormat() int16

	// PlanEncode returns an EncodePlan for encoding value into PostgreSQL format for oid and format. If no plan can be
	// found then nil is returned.
	PlanEncode(m *Map, oid uint32, format int16, value any) EncodePlan

	// PlanScan returns a ScanPlan for scanning a PostgreSQL value into a destination with the same type as target. If
	// no plan can be found then nil is returned.
	PlanScan(m *Map, oid uint32, format int16, target any) ScanPlan

	// DecodeDatabaseSQLValue returns src decoded into a value compatible with the sql.Scanner interface.
	DecodeDatabaseSQLValue(m *Map, oid uint32, format int16, src []byte) (driver.Value, error)

	// DecodeValue returns src decoded into its default format.
	DecodeValue(m *Map, oid uint32, format int16, src []byte) (any, error)
}

type nullAssignmentError struct {
	dst any
}

func ( *nullAssignmentError) () string {
	return fmt.Sprintf("cannot assign NULL to %T", .dst)
}

// Type represents a PostgreSQL data type. It must not be mutated after it is registered with a Map.
type Type struct {
	Codec Codec
	Name  string
	OID   uint32
}

// Map is the mapping between PostgreSQL server types and Go type handling logic. It can encode values for
// transmission to a PostgreSQL server and scan received values.
type Map struct {
	oidToType         map[uint32]*Type
	nameToType        map[string]*Type
	reflectTypeToName map[reflect.Type]string
	oidToFormatCode   map[uint32]int16

	reflectTypeToType map[reflect.Type]*Type

	memoizedScanPlans   map[uint32]map[reflect.Type][2]ScanPlan
	memoizedEncodePlans map[uint32]map[reflect.Type][2]EncodePlan

	// TryWrapEncodePlanFuncs is a slice of functions that will wrap a value that cannot be encoded by the Codec. Every
	// time a wrapper is found the PlanEncode method will be recursively called with the new value. This allows several layers of wrappers
	// to be built up. There are default functions placed in this slice by NewMap(). In most cases these functions
	// should run last. i.e. Additional functions should typically be prepended not appended.
	TryWrapEncodePlanFuncs []TryWrapEncodePlanFunc

	// TryWrapScanPlanFuncs is a slice of functions that will wrap a target that cannot be scanned into by the Codec. Every
	// time a wrapper is found the PlanScan method will be recursively called with the new target. This allows several layers of wrappers
	// to be built up. There are default functions placed in this slice by NewMap(). In most cases these functions
	// should run last. i.e. Additional functions should typically be prepended not appended.
	TryWrapScanPlanFuncs []TryWrapScanPlanFunc
}

func () *Map {
	defaultMapInitOnce.Do(initDefaultMap)

	return &Map{
		oidToType:         make(map[uint32]*Type),
		nameToType:        make(map[string]*Type),
		reflectTypeToName: make(map[reflect.Type]string),
		oidToFormatCode:   make(map[uint32]int16),

		memoizedScanPlans:   make(map[uint32]map[reflect.Type][2]ScanPlan),
		memoizedEncodePlans: make(map[uint32]map[reflect.Type][2]EncodePlan),

		TryWrapEncodePlanFuncs: []TryWrapEncodePlanFunc{
			TryWrapDerefPointerEncodePlan,
			TryWrapBuiltinTypeEncodePlan,
			TryWrapFindUnderlyingTypeEncodePlan,
			TryWrapStructEncodePlan,
			TryWrapSliceEncodePlan,
			TryWrapMultiDimSliceEncodePlan,
			TryWrapArrayEncodePlan,
		},

		TryWrapScanPlanFuncs: []TryWrapScanPlanFunc{
			TryPointerPointerScanPlan,
			TryWrapBuiltinTypeScanPlan,
			TryFindUnderlyingTypeScanPlan,
			TryWrapStructScanPlan,
			TryWrapPtrSliceScanPlan,
			TryWrapPtrMultiDimSliceScanPlan,
			TryWrapPtrArrayScanPlan,
		},
	}
}

// RegisterType registers a data type with the Map. t must not be mutated after it is registered.
func ( *Map) ( *Type) {
	.oidToType[.OID] = 
	.nameToType[.Name] = 
	.oidToFormatCode[.OID] = .Codec.PreferredFormat()

	// Invalidated by type registration
	.reflectTypeToType = nil
	for  := range .memoizedScanPlans {
		delete(.memoizedScanPlans, )
	}
	for  := range .memoizedEncodePlans {
		delete(.memoizedEncodePlans, )
	}
}

// RegisterDefaultPgType registers a mapping of a Go type to a PostgreSQL type name. Typically the data type to be
// encoded or decoded is determined by the PostgreSQL OID. But if the OID of a value to be encoded or decoded is
// unknown, this additional mapping will be used by TypeForValue to determine a suitable data type.
func ( *Map) ( any,  string) {
	.reflectTypeToName[reflect.TypeOf()] = 

	// Invalidated by type registration
	.reflectTypeToType = nil
	for  := range .memoizedScanPlans {
		delete(.memoizedScanPlans, )
	}
	for  := range .memoizedEncodePlans {
		delete(.memoizedEncodePlans, )
	}
}

// TypeForOID returns the Type registered for the given OID. The returned Type must not be mutated.
func ( *Map) ( uint32) (*Type, bool) {
	if ,  := .oidToType[];  {
		return , true
	}

	,  := defaultMap.oidToType[]
	return , 
}

// TypeForName returns the Type registered for the given name. The returned Type must not be mutated.
func ( *Map) ( string) (*Type, bool) {
	if ,  := .nameToType[];  {
		return , true
	}
	,  := defaultMap.nameToType[]
	return , 
}

func ( *Map) () {
	.reflectTypeToType = make(map[reflect.Type]*Type)

	for ,  := range .reflectTypeToName {
		if ,  := .TypeForName();  {
			.reflectTypeToType[] = 
		}
	}
}

// TypeForValue finds a data type suitable for v. Use RegisterType to register types that can encode and decode
// themselves. Use RegisterDefaultPgType to register that can be handled by a registered data type.  The returned Type
// must not be mutated.
func ( *Map) ( any) (*Type, bool) {
	if .reflectTypeToType == nil {
		.buildReflectTypeToType()
	}

	if ,  := .reflectTypeToType[reflect.TypeOf()];  {
		return , true
	}

	,  := defaultMap.reflectTypeToType[reflect.TypeOf()]
	return , 
}

// FormatCodeForOID returns the preferred format code for type oid. If the type is not registered it returns the text
// format code.
func ( *Map) ( uint32) int16 {
	if ,  := .oidToFormatCode[];  {
		return 
	}

	if ,  := defaultMap.oidToFormatCode[];  {
		return 
	}

	return TextFormatCode
}

// EncodePlan is a precompiled plan to encode a particular type into a particular OID and format.
type EncodePlan interface {
	// Encode appends the encoded bytes of value to buf. If value is the SQL value NULL then append nothing and return
	// (nil, nil). The caller of Encode is responsible for writing the correct NULL value or the length of the data
	// written.
	Encode(value any, buf []byte) (newBuf []byte, err error)
}

// ScanPlan is a precompiled plan to scan into a type of destination.
type ScanPlan interface {
	// Scan scans src into target. src is only valid during the call to Scan. The ScanPlan must not retain a reference to
	// src.
	Scan(src []byte, target any) error
}

type scanPlanCodecSQLScanner struct {
	c          Codec
	m          *Map
	oid        uint32
	formatCode int16
}

func ( *scanPlanCodecSQLScanner) ( []byte,  any) error {
	,  := .c.DecodeDatabaseSQLValue(.m, .oid, .formatCode, )
	if  != nil {
		return 
	}

	 := .(sql.Scanner)
	return .Scan()
}

type scanPlanSQLScanner struct {
	formatCode int16
}

func ( *scanPlanSQLScanner) ( []byte,  any) error {
	 := .(sql.Scanner)
	if  == nil {
		// This is necessary because interface value []byte:nil does not equal nil:nil for the binary format path and the
		// text format path would be converted to empty string.
		return .Scan(nil)
	} else if .formatCode == BinaryFormatCode {
		return .Scan()
	} else {
		return .Scan(string())
	}
}

type scanPlanString struct{}

func (scanPlanString) ( []byte,  any) error {
	if  == nil {
		return fmt.Errorf("cannot scan NULL into %T", )
	}

	 := ().(*string)
	* = string()
	return nil
}

type scanPlanAnyTextToBytes struct{}

func (scanPlanAnyTextToBytes) ( []byte,  any) error {
	 := .(*[]byte)
	if  == nil {
		* = nil
		return nil
	}

	* = make([]byte, len())
	copy(*, )
	return nil
}

type scanPlanFail struct {
	m          *Map
	oid        uint32
	formatCode int16
}

func ( *scanPlanFail) ( []byte,  any) error {
	// If src is NULL it might be possible to scan into dst even though it is the types are not compatible. While this
	// may seem to be a contrived case it can occur when selecting NULL directly. PostgreSQL assigns it the type of text.
	// It would be surprising to the caller to have to cast the NULL (e.g. `select null::int`). So try to figure out a
	// compatible data type for dst and scan with that.
	//
	// See https://github.com/jackc/pgx/issues/1326
	if  == nil {
		// As a horrible hack try all types to find anything that can scan into dst.
		for  := range .m.oidToType {
			// using planScan instead of Scan or PlanScan to avoid polluting the planned scan cache.
			 := .m.planScan(, .formatCode, )
			if ,  := .(*scanPlanFail); ! {
				return .Scan(, )
			}
		}
		for  := range defaultMap.oidToType {
			if ,  := .m.oidToType[]; ! {
				 := .m.planScan(, .formatCode, )
				if ,  := .(*scanPlanFail); ! {
					return .Scan(, )
				}
			}
		}
	}

	var  string
	switch .formatCode {
	case TextFormatCode:
		 = "text"
	case BinaryFormatCode:
		 = "binary"
	default:
		 = fmt.Sprintf("unknown %d", .formatCode)
	}

	var  string
	if ,  := .m.TypeForOID(.oid);  {
		 = .Name
	} else {
		 = "unknown type"
	}

	return fmt.Errorf("cannot scan %s (OID %d) in %v format into %T", , .oid, , )
}

// TryWrapScanPlanFunc is a function that tries to create a wrapper plan for target. If successful it returns a plan
// that will convert the target passed to Scan and then call the next plan. nextTarget is target as it will be converted
// by plan. It must be used to find another suitable ScanPlan. When it is found SetNext must be called on plan for it
// to be usabled. ok indicates if a suitable wrapper was found.
type TryWrapScanPlanFunc func(target any) (plan WrappedScanPlanNextSetter, nextTarget any, ok bool)

type pointerPointerScanPlan struct {
	dstType reflect.Type
	next    ScanPlan
}

func ( *pointerPointerScanPlan) ( ScanPlan) { .next =  }

func ( *pointerPointerScanPlan) ( []byte,  any) error {
	 := reflect.ValueOf().Elem()
	if  == nil {
		.Set(reflect.Zero(.Type()))
		return nil
	}

	.Set(reflect.New(.Type().Elem()))
	return .next.Scan(, .Interface())
}

// TryPointerPointerScanPlan handles a pointer to a pointer by setting the target to nil for SQL NULL and allocating and
// scanning for non-NULL.
func ( any) ( WrappedScanPlanNextSetter,  any,  bool) {
	if  := reflect.ValueOf(); .Kind() == reflect.Ptr {
		 := .Elem()
		if .Kind() == reflect.Ptr {
			 = &pointerPointerScanPlan{dstType: .Type()}
			return , reflect.Zero(.Type()).Interface(), true
		}
	}

	return nil, nil, false
}

// SkipUnderlyingTypePlanner prevents PlanScan and PlanDecode from trying to use the underlying type.
type SkipUnderlyingTypePlanner interface {
	SkipUnderlyingTypePlan()
}

var elemKindToPointerTypes map[reflect.Kind]reflect.Type = map[reflect.Kind]reflect.Type{
	reflect.Int:     reflect.TypeOf(new(int)),
	reflect.Int8:    reflect.TypeOf(new(int8)),
	reflect.Int16:   reflect.TypeOf(new(int16)),
	reflect.Int32:   reflect.TypeOf(new(int32)),
	reflect.Int64:   reflect.TypeOf(new(int64)),
	reflect.Uint:    reflect.TypeOf(new(uint)),
	reflect.Uint8:   reflect.TypeOf(new(uint8)),
	reflect.Uint16:  reflect.TypeOf(new(uint16)),
	reflect.Uint32:  reflect.TypeOf(new(uint32)),
	reflect.Uint64:  reflect.TypeOf(new(uint64)),
	reflect.Float32: reflect.TypeOf(new(float32)),
	reflect.Float64: reflect.TypeOf(new(float64)),
	reflect.String:  reflect.TypeOf(new(string)),
	reflect.Bool:    reflect.TypeOf(new(bool)),
}

type underlyingTypeScanPlan struct {
	dstType     reflect.Type
	nextDstType reflect.Type
	next        ScanPlan
}

func ( *underlyingTypeScanPlan) ( ScanPlan) { .next =  }

func ( *underlyingTypeScanPlan) ( []byte,  any) error {
	return .next.Scan(, reflect.ValueOf().Convert(.nextDstType).Interface())
}

// TryFindUnderlyingTypeScanPlan tries to convert to a Go builtin type. e.g. If value was of type MyString and
// MyString was defined as a string then a wrapper plan would be returned that converts MyString to string.
func ( any) ( WrappedScanPlanNextSetter,  any,  bool) {
	if ,  := .(SkipUnderlyingTypePlanner);  {
		return nil, nil, false
	}

	 := reflect.ValueOf()

	if .Kind() == reflect.Ptr {
		var  reflect.Value
		if .IsNil() {
			 = reflect.New(.Type().Elem()).Elem()
		} else {
			 = .Elem()
		}
		 := elemKindToPointerTypes[.Kind()]
		if  == nil && .Kind() == reflect.Slice {
			if .Type().Elem().Kind() == reflect.Uint8 {
				var  *[]byte
				 = reflect.TypeOf()
			}
		}

		if  != nil && .Type() !=  {
			return &underlyingTypeScanPlan{dstType: .Type(), nextDstType: }, .Convert().Interface(), true
		}

	}

	return nil, nil, false
}

type WrappedScanPlanNextSetter interface {
	SetNext(ScanPlan)
	ScanPlan
}

// TryWrapBuiltinTypeScanPlan tries to wrap a builtin type with a wrapper that provides additional methods. e.g. If
// value was of type int32 then a wrapper plan would be returned that converts target to a value that implements
// Int64Scanner.
func ( any) ( WrappedScanPlanNextSetter,  any,  bool) {
	switch target := .(type) {
	case *int8:
		return &wrapInt8ScanPlan{}, (*int8Wrapper)(), true
	case *int16:
		return &wrapInt16ScanPlan{}, (*int16Wrapper)(), true
	case *int32:
		return &wrapInt32ScanPlan{}, (*int32Wrapper)(), true
	case *int64:
		return &wrapInt64ScanPlan{}, (*int64Wrapper)(), true
	case *int:
		return &wrapIntScanPlan{}, (*intWrapper)(), true
	case *uint8:
		return &wrapUint8ScanPlan{}, (*uint8Wrapper)(), true
	case *uint16:
		return &wrapUint16ScanPlan{}, (*uint16Wrapper)(), true
	case *uint32:
		return &wrapUint32ScanPlan{}, (*uint32Wrapper)(), true
	case *uint64:
		return &wrapUint64ScanPlan{}, (*uint64Wrapper)(), true
	case *uint:
		return &wrapUintScanPlan{}, (*uintWrapper)(), true
	case *float32:
		return &wrapFloat32ScanPlan{}, (*float32Wrapper)(), true
	case *float64:
		return &wrapFloat64ScanPlan{}, (*float64Wrapper)(), true
	case *string:
		return &wrapStringScanPlan{}, (*stringWrapper)(), true
	case *time.Time:
		return &wrapTimeScanPlan{}, (*timeWrapper)(), true
	case *time.Duration:
		return &wrapDurationScanPlan{}, (*durationWrapper)(), true
	case *net.IPNet:
		return &wrapNetIPNetScanPlan{}, (*netIPNetWrapper)(), true
	case *net.IP:
		return &wrapNetIPScanPlan{}, (*netIPWrapper)(), true
	case *netip.Prefix:
		return &wrapNetipPrefixScanPlan{}, (*netipPrefixWrapper)(), true
	case *netip.Addr:
		return &wrapNetipAddrScanPlan{}, (*netipAddrWrapper)(), true
	case *map[string]*string:
		return &wrapMapStringToPointerStringScanPlan{}, (*mapStringToPointerStringWrapper)(), true
	case *map[string]string:
		return &wrapMapStringToStringScanPlan{}, (*mapStringToStringWrapper)(), true
	case *[16]byte:
		return &wrapByte16ScanPlan{}, (*byte16Wrapper)(), true
	case *[]byte:
		return &wrapByteSliceScanPlan{}, (*byteSliceWrapper)(), true
	}

	return nil, nil, false
}

type wrapInt8ScanPlan struct {
	next ScanPlan
}

func ( *wrapInt8ScanPlan) ( ScanPlan) { .next =  }

func ( *wrapInt8ScanPlan) ( []byte,  any) error {
	return .next.Scan(, (*int8Wrapper)(.(*int8)))
}

type wrapInt16ScanPlan struct {
	next ScanPlan
}

func ( *wrapInt16ScanPlan) ( ScanPlan) { .next =  }

func ( *wrapInt16ScanPlan) ( []byte,  any) error {
	return .next.Scan(, (*int16Wrapper)(.(*int16)))
}

type wrapInt32ScanPlan struct {
	next ScanPlan
}

func ( *wrapInt32ScanPlan) ( ScanPlan) { .next =  }

func ( *wrapInt32ScanPlan) ( []byte,  any) error {
	return .next.Scan(, (*int32Wrapper)(.(*int32)))
}

type wrapInt64ScanPlan struct {
	next ScanPlan
}

func ( *wrapInt64ScanPlan) ( ScanPlan) { .next =  }

func ( *wrapInt64ScanPlan) ( []byte,  any) error {
	return .next.Scan(, (*int64Wrapper)(.(*int64)))
}

type wrapIntScanPlan struct {
	next ScanPlan
}

func ( *wrapIntScanPlan) ( ScanPlan) { .next =  }

func ( *wrapIntScanPlan) ( []byte,  any) error {
	return .next.Scan(, (*intWrapper)(.(*int)))
}

type wrapUint8ScanPlan struct {
	next ScanPlan
}

func ( *wrapUint8ScanPlan) ( ScanPlan) { .next =  }

func ( *wrapUint8ScanPlan) ( []byte,  any) error {
	return .next.Scan(, (*uint8Wrapper)(.(*uint8)))
}

type wrapUint16ScanPlan struct {
	next ScanPlan
}

func ( *wrapUint16ScanPlan) ( ScanPlan) { .next =  }

func ( *wrapUint16ScanPlan) ( []byte,  any) error {
	return .next.Scan(, (*uint16Wrapper)(.(*uint16)))
}

type wrapUint32ScanPlan struct {
	next ScanPlan
}

func ( *wrapUint32ScanPlan) ( ScanPlan) { .next =  }

func ( *wrapUint32ScanPlan) ( []byte,  any) error {
	return .next.Scan(, (*uint32Wrapper)(.(*uint32)))
}

type wrapUint64ScanPlan struct {
	next ScanPlan
}

func ( *wrapUint64ScanPlan) ( ScanPlan) { .next =  }

func ( *wrapUint64ScanPlan) ( []byte,  any) error {
	return .next.Scan(, (*uint64Wrapper)(.(*uint64)))
}

type wrapUintScanPlan struct {
	next ScanPlan
}

func ( *wrapUintScanPlan) ( ScanPlan) { .next =  }

func ( *wrapUintScanPlan) ( []byte,  any) error {
	return .next.Scan(, (*uintWrapper)(.(*uint)))
}

type wrapFloat32ScanPlan struct {
	next ScanPlan
}

func ( *wrapFloat32ScanPlan) ( ScanPlan) { .next =  }

func ( *wrapFloat32ScanPlan) ( []byte,  any) error {
	return .next.Scan(, (*float32Wrapper)(.(*float32)))
}

type wrapFloat64ScanPlan struct {
	next ScanPlan
}

func ( *wrapFloat64ScanPlan) ( ScanPlan) { .next =  }

func ( *wrapFloat64ScanPlan) ( []byte,  any) error {
	return .next.Scan(, (*float64Wrapper)(.(*float64)))
}

type wrapStringScanPlan struct {
	next ScanPlan
}

func ( *wrapStringScanPlan) ( ScanPlan) { .next =  }

func ( *wrapStringScanPlan) ( []byte,  any) error {
	return .next.Scan(, (*stringWrapper)(.(*string)))
}

type wrapTimeScanPlan struct {
	next ScanPlan
}

func ( *wrapTimeScanPlan) ( ScanPlan) { .next =  }

func ( *wrapTimeScanPlan) ( []byte,  any) error {
	return .next.Scan(, (*timeWrapper)(.(*time.Time)))
}

type wrapDurationScanPlan struct {
	next ScanPlan
}

func ( *wrapDurationScanPlan) ( ScanPlan) { .next =  }

func ( *wrapDurationScanPlan) ( []byte,  any) error {
	return .next.Scan(, (*durationWrapper)(.(*time.Duration)))
}

type wrapNetIPNetScanPlan struct {
	next ScanPlan
}

func ( *wrapNetIPNetScanPlan) ( ScanPlan) { .next =  }

func ( *wrapNetIPNetScanPlan) ( []byte,  any) error {
	return .next.Scan(, (*netIPNetWrapper)(.(*net.IPNet)))
}

type wrapNetIPScanPlan struct {
	next ScanPlan
}

func ( *wrapNetIPScanPlan) ( ScanPlan) { .next =  }

func ( *wrapNetIPScanPlan) ( []byte,  any) error {
	return .next.Scan(, (*netIPWrapper)(.(*net.IP)))
}

type wrapNetipPrefixScanPlan struct {
	next ScanPlan
}

func ( *wrapNetipPrefixScanPlan) ( ScanPlan) { .next =  }

func ( *wrapNetipPrefixScanPlan) ( []byte,  any) error {
	return .next.Scan(, (*netipPrefixWrapper)(.(*netip.Prefix)))
}

type wrapNetipAddrScanPlan struct {
	next ScanPlan
}

func ( *wrapNetipAddrScanPlan) ( ScanPlan) { .next =  }

func ( *wrapNetipAddrScanPlan) ( []byte,  any) error {
	return .next.Scan(, (*netipAddrWrapper)(.(*netip.Addr)))
}

type wrapMapStringToPointerStringScanPlan struct {
	next ScanPlan
}

func ( *wrapMapStringToPointerStringScanPlan) ( ScanPlan) { .next =  }

func ( *wrapMapStringToPointerStringScanPlan) ( []byte,  any) error {
	return .next.Scan(, (*mapStringToPointerStringWrapper)(.(*map[string]*string)))
}

type wrapMapStringToStringScanPlan struct {
	next ScanPlan
}

func ( *wrapMapStringToStringScanPlan) ( ScanPlan) { .next =  }

func ( *wrapMapStringToStringScanPlan) ( []byte,  any) error {
	return .next.Scan(, (*mapStringToStringWrapper)(.(*map[string]string)))
}

type wrapByte16ScanPlan struct {
	next ScanPlan
}

func ( *wrapByte16ScanPlan) ( ScanPlan) { .next =  }

func ( *wrapByte16ScanPlan) ( []byte,  any) error {
	return .next.Scan(, (*byte16Wrapper)(.(*[16]byte)))
}

type wrapByteSliceScanPlan struct {
	next ScanPlan
}

func ( *wrapByteSliceScanPlan) ( ScanPlan) { .next =  }

func ( *wrapByteSliceScanPlan) ( []byte,  any) error {
	return .next.Scan(, (*byteSliceWrapper)(.(*[]byte)))
}

type pointerEmptyInterfaceScanPlan struct {
	codec      Codec
	m          *Map
	oid        uint32
	formatCode int16
}

func ( *pointerEmptyInterfaceScanPlan) ( []byte,  any) error {
	,  := .codec.DecodeValue(.m, .oid, .formatCode, )
	if  != nil {
		return 
	}

	 := .(*any)
	* = 

	return nil
}

// TryWrapStructPlan tries to wrap a struct with a wrapper that implements CompositeIndexGetter.
func ( any) ( WrappedScanPlanNextSetter,  any,  bool) {
	 := reflect.ValueOf()
	if .Kind() != reflect.Ptr {
		return nil, nil, false
	}

	var  reflect.Value
	if .IsNil() {
		 = reflect.Zero(.Type().Elem())
	} else {
		 = .Elem()
	}
	 := .Type()

	if .Kind() == reflect.Struct {
		 := getExportedFieldValues()
		if len() == 0 {
			return nil, nil, false
		}

		 := ptrStructWrapper{
			s:              ,
			exportedFields: ,
		}
		return &wrapAnyPtrStructScanPlan{}, &, true
	}

	return nil, nil, false
}

type wrapAnyPtrStructScanPlan struct {
	next ScanPlan
}

func ( *wrapAnyPtrStructScanPlan) ( ScanPlan) { .next =  }

func ( *wrapAnyPtrStructScanPlan) ( []byte,  any) error {
	 := ptrStructWrapper{
		s:              ,
		exportedFields: getExportedFieldValues(reflect.ValueOf().Elem()),
	}

	return .next.Scan(, &)
}

// TryWrapPtrSliceScanPlan tries to wrap a pointer to a single dimension slice.
func ( any) ( WrappedScanPlanNextSetter,  any,  bool) {
	// Avoid using reflect path for common types.
	switch target := .(type) {
	case *[]int16:
		return &wrapPtrSliceScanPlan[int16]{}, (*FlatArray[int16])(), true
	case *[]int32:
		return &wrapPtrSliceScanPlan[int32]{}, (*FlatArray[int32])(), true
	case *[]int64:
		return &wrapPtrSliceScanPlan[int64]{}, (*FlatArray[int64])(), true
	case *[]float32:
		return &wrapPtrSliceScanPlan[float32]{}, (*FlatArray[float32])(), true
	case *[]float64:
		return &wrapPtrSliceScanPlan[float64]{}, (*FlatArray[float64])(), true
	case *[]string:
		return &wrapPtrSliceScanPlan[string]{}, (*FlatArray[string])(), true
	case *[]time.Time:
		return &wrapPtrSliceScanPlan[time.Time]{}, (*FlatArray[time.Time])(), true
	}

	 := reflect.TypeOf()
	if .Kind() != reflect.Ptr {
		return nil, nil, false
	}

	 := .Elem()

	if .Kind() == reflect.Slice {
		 := reflect.New().Elem()
		return &wrapPtrSliceReflectScanPlan{}, &anySliceArrayReflect{slice: }, true
	}
	return nil, nil, false
}

type wrapPtrSliceScanPlan[ any] struct {
	next ScanPlan
}

func ( *wrapPtrSliceScanPlan[]) ( ScanPlan) { .next =  }

func ( *wrapPtrSliceScanPlan[]) ( []byte,  any) error {
	return .next.Scan(, (*FlatArray[])(.(*[])))
}

type wrapPtrSliceReflectScanPlan struct {
	next ScanPlan
}

func ( *wrapPtrSliceReflectScanPlan) ( ScanPlan) { .next =  }

func ( *wrapPtrSliceReflectScanPlan) ( []byte,  any) error {
	return .next.Scan(, &anySliceArrayReflect{slice: reflect.ValueOf().Elem()})
}

// TryWrapPtrMultiDimSliceScanPlan tries to wrap a pointer to a multi-dimension slice.
func ( any) ( WrappedScanPlanNextSetter,  any,  bool) {
	 := reflect.ValueOf()
	if .Kind() != reflect.Ptr {
		return nil, nil, false
	}

	 := .Elem()

	if .Kind() == reflect.Slice {
		 := .Type().Elem().Kind()
		if  == reflect.Slice {
			if !isRagged() {
				return &wrapPtrMultiDimSliceScanPlan{}, &anyMultiDimSliceArray{slice: .Elem()}, true
			}
		}
	}

	return nil, nil, false
}

type wrapPtrMultiDimSliceScanPlan struct {
	next ScanPlan
}

func ( *wrapPtrMultiDimSliceScanPlan) ( ScanPlan) { .next =  }

func ( *wrapPtrMultiDimSliceScanPlan) ( []byte,  any) error {
	return .next.Scan(, &anyMultiDimSliceArray{slice: reflect.ValueOf().Elem()})
}

// TryWrapPtrArrayScanPlan tries to wrap a pointer to a single dimension array.
func ( any) ( WrappedScanPlanNextSetter,  any,  bool) {
	 := reflect.ValueOf()
	if .Kind() != reflect.Ptr {
		return nil, nil, false
	}

	 := .Elem()

	if .Kind() == reflect.Array {
		return &wrapPtrArrayReflectScanPlan{}, &anyArrayArrayReflect{array: }, true
	}
	return nil, nil, false
}

type wrapPtrArrayReflectScanPlan struct {
	next ScanPlan
}

func ( *wrapPtrArrayReflectScanPlan) ( ScanPlan) { .next =  }

func ( *wrapPtrArrayReflectScanPlan) ( []byte,  any) error {
	return .next.Scan(, &anyArrayArrayReflect{array: reflect.ValueOf().Elem()})
}

// PlanScan prepares a plan to scan a value into target.
func ( *Map) ( uint32,  int16,  any) ScanPlan {
	 := .memoizedScanPlans[]
	if  == nil {
		 = make(map[reflect.Type][2]ScanPlan)
		.memoizedScanPlans[] = 
	}
	 := reflect.TypeOf()
	 := []
	 := []
	if  == nil {
		 = .planScan(, , )
		[] = 
		[] = 
	}

	return 
}

func ( *Map) ( uint32,  int16,  any) ScanPlan {
	if  == nil {
		return &scanPlanFail{m: , oid: , formatCode: }
	}

	if ,  := .(*UndecodedBytes);  {
		return scanPlanAnyToUndecodedBytes{}
	}

	switch  {
	case BinaryFormatCode:
		switch .(type) {
		case *string:
			switch  {
			case TextOID, VarcharOID:
				return scanPlanString{}
			}
		}
	case TextFormatCode:
		switch .(type) {
		case *string:
			return scanPlanString{}
		case *[]byte:
			if  != ByteaOID {
				return scanPlanAnyTextToBytes{}
			}
		case TextScanner:
			return scanPlanTextAnyToTextScanner{}
		}
	}

	var  *Type

	if ,  := .TypeForOID();  {
		 = 
	} else if ,  := .TypeForValue();  {
		 = 
		 = .OID // Preserve assumed OID in case we are recursively called below.
	}

	if  != nil {
		if  := .Codec.PlanScan(, , , );  != nil {
			return 
		}
	}

	// This needs to happen before trying m.TryWrapScanPlanFuncs. Otherwise, a sql.Scanner would not get called if it was
	// defined on a type that could be unwrapped such as `type myString string`.
	//
	//  https://github.com/jackc/pgtype/issues/197
	if ,  := .(sql.Scanner);  {
		if  == nil {
			return &scanPlanSQLScanner{formatCode: }
		} else {
			return &scanPlanCodecSQLScanner{c: .Codec, m: , oid: , formatCode: }
		}
	}

	for ,  := range .TryWrapScanPlanFuncs {
		if , ,  := ();  {
			if  := .(, , );  != nil {
				if ,  := .(*scanPlanFail); ! {
					.SetNext()
					return 
				}
			}
		}
	}

	if  != nil {
		if ,  := .(*any);  {
			return &pointerEmptyInterfaceScanPlan{codec: .Codec, m: , oid: , formatCode: }
		}
	}

	return &scanPlanFail{m: , oid: , formatCode: }
}

func ( *Map) ( uint32,  int16,  []byte,  any) error {
	if  == nil {
		return nil
	}

	 := .PlanScan(, , )
	return .Scan(, )
}

var ErrScanTargetTypeChanged = errors.New("scan target type changed")

func codecScan( Codec,  *Map,  uint32,  int16,  []byte,  any) error {
	 := .PlanScan(, , , )
	if  == nil {
		return fmt.Errorf("PlanScan did not find a plan")
	}
	return .Scan(, )
}

func codecDecodeToTextFormat( Codec,  *Map,  uint32,  int16,  []byte) (driver.Value, error) {
	if  == nil {
		return nil, nil
	}

	if  == TextFormatCode {
		return string(), nil
	} else {
		,  := .DecodeValue(, , , )
		if  != nil {
			return nil, 
		}
		,  := .Encode(, TextFormatCode, , nil)
		if  != nil {
			return nil, 
		}
		return string(), nil
	}
}

// PlanEncode returns an Encode plan for encoding value into PostgreSQL format for oid and format. If no plan can be
// found then nil is returned.
func ( *Map) ( uint32,  int16,  any) EncodePlan {
	 := .memoizedEncodePlans[]
	if  == nil {
		 = make(map[reflect.Type][2]EncodePlan)
		.memoizedEncodePlans[] = 
	}
	 := reflect.TypeOf()
	 := []
	 := []
	if  == nil {
		 = .planEncode(, , )
		[] = 
		[] = 
	}

	return 
}

func ( *Map) ( uint32,  int16,  any) EncodePlan {
	if  == TextFormatCode {
		switch .(type) {
		case string:
			return encodePlanStringToAnyTextFormat{}
		case TextValuer:
			return encodePlanTextValuerToAnyTextFormat{}
		}
	}

	var  *Type
	if ,  := .TypeForOID();  {
		 = 
	} else {
		// If no type for the OID was found, then either it is unknowable (e.g. the simple protocol) or it is an
		// unregistered type. In either case try to find the type and OID that matches the value (e.g. a []byte would be
		// registered to PostgreSQL bytea).
		if ,  := .TypeForValue();  {
			 = 
			 = .OID // Preserve assumed OID in case we are recursively called below.
		}
	}

	if  != nil {
		if  := .Codec.PlanEncode(, , , );  != nil {
			return 
		}
	}

	for ,  := range .TryWrapEncodePlanFuncs {
		if , ,  := ();  {
			if  := .PlanEncode(, , );  != nil {
				.SetNext()
				return 
			}
		}
	}

	if ,  := .(driver.Valuer);  {
		return &encodePlanDriverValuer{m: , oid: , formatCode: }
	}

	return nil
}

type encodePlanStringToAnyTextFormat struct{}

func (encodePlanStringToAnyTextFormat) ( any,  []byte) ( []byte,  error) {
	 := .(string)
	return append(, ...), nil
}

type encodePlanTextValuerToAnyTextFormat struct{}

func (encodePlanTextValuerToAnyTextFormat) ( any,  []byte) ( []byte,  error) {
	,  := .(TextValuer).TextValue()
	if  != nil {
		return nil, 
	}
	if !.Valid {
		return nil, nil
	}

	return append(, .String...), nil
}

type encodePlanDriverValuer struct {
	m          *Map
	oid        uint32
	formatCode int16
}

func ( *encodePlanDriverValuer) ( any,  []byte) ( []byte,  error) {
	 := .(driver.Valuer)
	if  == nil {
		return nil, nil
	}
	,  := .Value()
	if  != nil {
		return nil, 
	}
	if  == nil {
		return nil, nil
	}

	,  = .m.Encode(.oid, .formatCode, , )
	if  == nil {
		return , nil
	}

	,  := .(string)
	if ! {
		return nil, 
	}

	var  any
	 := .m.Scan(.oid, TextFormatCode, []byte(), &)
	if  != nil {
		return nil, 
	}

	// Prevent infinite loop. We can't encode this. See https://github.com/jackc/pgx/issues/1331.
	if reflect.TypeOf() == reflect.TypeOf() {
		return nil, fmt.Errorf("tried to encode %v via encoding to text and scanning but failed due to receiving same type back", )
	}

	var  error
	,  = .m.Encode(.oid, BinaryFormatCode, , )
	if  != nil {
		return nil, 
	}

	return , nil
}

// TryWrapEncodePlanFunc is a function that tries to create a wrapper plan for value. If successful it returns a plan
// that will convert the value passed to Encode and then call the next plan. nextValue is value as it will be converted
// by plan. It must be used to find another suitable EncodePlan. When it is found SetNext must be called on plan for it
// to be usabled. ok indicates if a suitable wrapper was found.
type TryWrapEncodePlanFunc func(value any) (plan WrappedEncodePlanNextSetter, nextValue any, ok bool)

type derefPointerEncodePlan struct {
	next EncodePlan
}

func ( *derefPointerEncodePlan) ( EncodePlan) { .next =  }

func ( *derefPointerEncodePlan) ( any,  []byte) ( []byte,  error) {
	 := reflect.ValueOf()

	if .IsNil() {
		return nil, nil
	}

	return .next.Encode(.Elem().Interface(), )
}

// TryWrapDerefPointerEncodePlan tries to dereference a pointer. e.g. If value was of type *string then a wrapper plan
// would be returned that derefences the value.
func ( any) ( WrappedEncodePlanNextSetter,  any,  bool) {
	if ,  := .(driver.Valuer);  {
		return nil, nil, false
	}

	if  := reflect.TypeOf();  != nil && .Kind() == reflect.Ptr {
		return &derefPointerEncodePlan{}, reflect.New(.Elem()).Elem().Interface(), true
	}

	return nil, nil, false
}

var kindToTypes map[reflect.Kind]reflect.Type = map[reflect.Kind]reflect.Type{
	reflect.Int:     reflect.TypeOf(int(0)),
	reflect.Int8:    reflect.TypeOf(int8(0)),
	reflect.Int16:   reflect.TypeOf(int16(0)),
	reflect.Int32:   reflect.TypeOf(int32(0)),
	reflect.Int64:   reflect.TypeOf(int64(0)),
	reflect.Uint:    reflect.TypeOf(uint(0)),
	reflect.Uint8:   reflect.TypeOf(uint8(0)),
	reflect.Uint16:  reflect.TypeOf(uint16(0)),
	reflect.Uint32:  reflect.TypeOf(uint32(0)),
	reflect.Uint64:  reflect.TypeOf(uint64(0)),
	reflect.Float32: reflect.TypeOf(float32(0)),
	reflect.Float64: reflect.TypeOf(float64(0)),
	reflect.String:  reflect.TypeOf(""),
	reflect.Bool:    reflect.TypeOf(false),
}

type underlyingTypeEncodePlan struct {
	nextValueType reflect.Type
	next          EncodePlan
}

func ( *underlyingTypeEncodePlan) ( EncodePlan) { .next =  }

func ( *underlyingTypeEncodePlan) ( any,  []byte) ( []byte,  error) {
	return .next.Encode(reflect.ValueOf().Convert(.nextValueType).Interface(), )
}

// TryWrapFindUnderlyingTypeEncodePlan tries to convert to a Go builtin type. e.g. If value was of type MyString and
// MyString was defined as a string then a wrapper plan would be returned that converts MyString to string.
func ( any) ( WrappedEncodePlanNextSetter,  any,  bool) {
	if ,  := .(driver.Valuer);  {
		return nil, nil, false
	}

	if ,  := .(SkipUnderlyingTypePlanner);  {
		return nil, nil, false
	}

	 := reflect.ValueOf()

	 := kindToTypes[.Kind()]
	if  != nil && .Type() !=  {
		return &underlyingTypeEncodePlan{nextValueType: }, .Convert().Interface(), true
	}

	return nil, nil, false
}

type WrappedEncodePlanNextSetter interface {
	SetNext(EncodePlan)
	EncodePlan
}

// TryWrapBuiltinTypeEncodePlan tries to wrap a builtin type with a wrapper that provides additional methods. e.g. If
// value was of type int32 then a wrapper plan would be returned that converts value to a type that implements
// Int64Valuer.
func ( any) ( WrappedEncodePlanNextSetter,  any,  bool) {
	if ,  := .(driver.Valuer);  {
		return nil, nil, false
	}

	switch value := .(type) {
	case int8:
		return &wrapInt8EncodePlan{}, int8Wrapper(), true
	case int16:
		return &wrapInt16EncodePlan{}, int16Wrapper(), true
	case int32:
		return &wrapInt32EncodePlan{}, int32Wrapper(), true
	case int64:
		return &wrapInt64EncodePlan{}, int64Wrapper(), true
	case int:
		return &wrapIntEncodePlan{}, intWrapper(), true
	case uint8:
		return &wrapUint8EncodePlan{}, uint8Wrapper(), true
	case uint16:
		return &wrapUint16EncodePlan{}, uint16Wrapper(), true
	case uint32:
		return &wrapUint32EncodePlan{}, uint32Wrapper(), true
	case uint64:
		return &wrapUint64EncodePlan{}, uint64Wrapper(), true
	case uint:
		return &wrapUintEncodePlan{}, uintWrapper(), true
	case float32:
		return &wrapFloat32EncodePlan{}, float32Wrapper(), true
	case float64:
		return &wrapFloat64EncodePlan{}, float64Wrapper(), true
	case string:
		return &wrapStringEncodePlan{}, stringWrapper(), true
	case time.Time:
		return &wrapTimeEncodePlan{}, timeWrapper(), true
	case time.Duration:
		return &wrapDurationEncodePlan{}, durationWrapper(), true
	case net.IPNet:
		return &wrapNetIPNetEncodePlan{}, netIPNetWrapper(), true
	case net.IP:
		return &wrapNetIPEncodePlan{}, netIPWrapper(), true
	case netip.Prefix:
		return &wrapNetipPrefixEncodePlan{}, netipPrefixWrapper(), true
	case netip.Addr:
		return &wrapNetipAddrEncodePlan{}, netipAddrWrapper(), true
	case map[string]*string:
		return &wrapMapStringToPointerStringEncodePlan{}, mapStringToPointerStringWrapper(), true
	case map[string]string:
		return &wrapMapStringToStringEncodePlan{}, mapStringToStringWrapper(), true
	case [16]byte:
		return &wrapByte16EncodePlan{}, byte16Wrapper(), true
	case []byte:
		return &wrapByteSliceEncodePlan{}, byteSliceWrapper(), true
	case fmt.Stringer:
		return &wrapFmtStringerEncodePlan{}, fmtStringerWrapper{}, true
	}

	return nil, nil, false
}

type wrapInt8EncodePlan struct {
	next EncodePlan
}

func ( *wrapInt8EncodePlan) ( EncodePlan) { .next =  }

func ( *wrapInt8EncodePlan) ( any,  []byte) ( []byte,  error) {
	return .next.Encode(int8Wrapper(.(int8)), )
}

type wrapInt16EncodePlan struct {
	next EncodePlan
}

func ( *wrapInt16EncodePlan) ( EncodePlan) { .next =  }

func ( *wrapInt16EncodePlan) ( any,  []byte) ( []byte,  error) {
	return .next.Encode(int16Wrapper(.(int16)), )
}

type wrapInt32EncodePlan struct {
	next EncodePlan
}

func ( *wrapInt32EncodePlan) ( EncodePlan) { .next =  }

func ( *wrapInt32EncodePlan) ( any,  []byte) ( []byte,  error) {
	return .next.Encode(int32Wrapper(.(int32)), )
}

type wrapInt64EncodePlan struct {
	next EncodePlan
}

func ( *wrapInt64EncodePlan) ( EncodePlan) { .next =  }

func ( *wrapInt64EncodePlan) ( any,  []byte) ( []byte,  error) {
	return .next.Encode(int64Wrapper(.(int64)), )
}

type wrapIntEncodePlan struct {
	next EncodePlan
}

func ( *wrapIntEncodePlan) ( EncodePlan) { .next =  }

func ( *wrapIntEncodePlan) ( any,  []byte) ( []byte,  error) {
	return .next.Encode(intWrapper(.(int)), )
}

type wrapUint8EncodePlan struct {
	next EncodePlan
}

func ( *wrapUint8EncodePlan) ( EncodePlan) { .next =  }

func ( *wrapUint8EncodePlan) ( any,  []byte) ( []byte,  error) {
	return .next.Encode(uint8Wrapper(.(uint8)), )
}

type wrapUint16EncodePlan struct {
	next EncodePlan
}

func ( *wrapUint16EncodePlan) ( EncodePlan) { .next =  }

func ( *wrapUint16EncodePlan) ( any,  []byte) ( []byte,  error) {
	return .next.Encode(uint16Wrapper(.(uint16)), )
}

type wrapUint32EncodePlan struct {
	next EncodePlan
}

func ( *wrapUint32EncodePlan) ( EncodePlan) { .next =  }

func ( *wrapUint32EncodePlan) ( any,  []byte) ( []byte,  error) {
	return .next.Encode(uint32Wrapper(.(uint32)), )
}

type wrapUint64EncodePlan struct {
	next EncodePlan
}

func ( *wrapUint64EncodePlan) ( EncodePlan) { .next =  }

func ( *wrapUint64EncodePlan) ( any,  []byte) ( []byte,  error) {
	return .next.Encode(uint64Wrapper(.(uint64)), )
}

type wrapUintEncodePlan struct {
	next EncodePlan
}

func ( *wrapUintEncodePlan) ( EncodePlan) { .next =  }

func ( *wrapUintEncodePlan) ( any,  []byte) ( []byte,  error) {
	return .next.Encode(uintWrapper(.(uint)), )
}

type wrapFloat32EncodePlan struct {
	next EncodePlan
}

func ( *wrapFloat32EncodePlan) ( EncodePlan) { .next =  }

func ( *wrapFloat32EncodePlan) ( any,  []byte) ( []byte,  error) {
	return .next.Encode(float32Wrapper(.(float32)), )
}

type wrapFloat64EncodePlan struct {
	next EncodePlan
}

func ( *wrapFloat64EncodePlan) ( EncodePlan) { .next =  }

func ( *wrapFloat64EncodePlan) ( any,  []byte) ( []byte,  error) {
	return .next.Encode(float64Wrapper(.(float64)), )
}

type wrapStringEncodePlan struct {
	next EncodePlan
}

func ( *wrapStringEncodePlan) ( EncodePlan) { .next =  }

func ( *wrapStringEncodePlan) ( any,  []byte) ( []byte,  error) {
	return .next.Encode(stringWrapper(.(string)), )
}

type wrapTimeEncodePlan struct {
	next EncodePlan
}

func ( *wrapTimeEncodePlan) ( EncodePlan) { .next =  }

func ( *wrapTimeEncodePlan) ( any,  []byte) ( []byte,  error) {
	return .next.Encode(timeWrapper(.(time.Time)), )
}

type wrapDurationEncodePlan struct {
	next EncodePlan
}

func ( *wrapDurationEncodePlan) ( EncodePlan) { .next =  }

func ( *wrapDurationEncodePlan) ( any,  []byte) ( []byte,  error) {
	return .next.Encode(durationWrapper(.(time.Duration)), )
}

type wrapNetIPNetEncodePlan struct {
	next EncodePlan
}

func ( *wrapNetIPNetEncodePlan) ( EncodePlan) { .next =  }

func ( *wrapNetIPNetEncodePlan) ( any,  []byte) ( []byte,  error) {
	return .next.Encode(netIPNetWrapper(.(net.IPNet)), )
}

type wrapNetIPEncodePlan struct {
	next EncodePlan
}

func ( *wrapNetIPEncodePlan) ( EncodePlan) { .next =  }

func ( *wrapNetIPEncodePlan) ( any,  []byte) ( []byte,  error) {
	return .next.Encode(netIPWrapper(.(net.IP)), )
}

type wrapNetipPrefixEncodePlan struct {
	next EncodePlan
}

func ( *wrapNetipPrefixEncodePlan) ( EncodePlan) { .next =  }

func ( *wrapNetipPrefixEncodePlan) ( any,  []byte) ( []byte,  error) {
	return .next.Encode(netipPrefixWrapper(.(netip.Prefix)), )
}

type wrapNetipAddrEncodePlan struct {
	next EncodePlan
}

func ( *wrapNetipAddrEncodePlan) ( EncodePlan) { .next =  }

func ( *wrapNetipAddrEncodePlan) ( any,  []byte) ( []byte,  error) {
	return .next.Encode(netipAddrWrapper(.(netip.Addr)), )
}

type wrapMapStringToPointerStringEncodePlan struct {
	next EncodePlan
}

func ( *wrapMapStringToPointerStringEncodePlan) ( EncodePlan) { .next =  }

func ( *wrapMapStringToPointerStringEncodePlan) ( any,  []byte) ( []byte,  error) {
	return .next.Encode(mapStringToPointerStringWrapper(.(map[string]*string)), )
}

type wrapMapStringToStringEncodePlan struct {
	next EncodePlan
}

func ( *wrapMapStringToStringEncodePlan) ( EncodePlan) { .next =  }

func ( *wrapMapStringToStringEncodePlan) ( any,  []byte) ( []byte,  error) {
	return .next.Encode(mapStringToStringWrapper(.(map[string]string)), )
}

type wrapByte16EncodePlan struct {
	next EncodePlan
}

func ( *wrapByte16EncodePlan) ( EncodePlan) { .next =  }

func ( *wrapByte16EncodePlan) ( any,  []byte) ( []byte,  error) {
	return .next.Encode(byte16Wrapper(.([16]byte)), )
}

type wrapByteSliceEncodePlan struct {
	next EncodePlan
}

func ( *wrapByteSliceEncodePlan) ( EncodePlan) { .next =  }

func ( *wrapByteSliceEncodePlan) ( any,  []byte) ( []byte,  error) {
	return .next.Encode(byteSliceWrapper(.([]byte)), )
}

type wrapFmtStringerEncodePlan struct {
	next EncodePlan
}

func ( *wrapFmtStringerEncodePlan) ( EncodePlan) { .next =  }

func ( *wrapFmtStringerEncodePlan) ( any,  []byte) ( []byte,  error) {
	return .next.Encode(fmtStringerWrapper{.(fmt.Stringer)}, )
}

// TryWrapStructPlan tries to wrap a struct with a wrapper that implements CompositeIndexGetter.
func ( any) ( WrappedEncodePlanNextSetter,  any,  bool) {
	if ,  := .(driver.Valuer);  {
		return nil, nil, false
	}

	if  := reflect.TypeOf();  != nil && .Kind() == reflect.Struct {
		 := getExportedFieldValues(reflect.ValueOf())
		if len() == 0 {
			return nil, nil, false
		}

		 := structWrapper{
			s:              ,
			exportedFields: ,
		}
		return &wrapAnyStructEncodePlan{}, , true
	}

	return nil, nil, false
}

type wrapAnyStructEncodePlan struct {
	next EncodePlan
}

func ( *wrapAnyStructEncodePlan) ( EncodePlan) { .next =  }

func ( *wrapAnyStructEncodePlan) ( any,  []byte) ( []byte,  error) {
	 := structWrapper{
		s:              ,
		exportedFields: getExportedFieldValues(reflect.ValueOf()),
	}

	return .next.Encode(, )
}

func getExportedFieldValues( reflect.Value) []reflect.Value {
	 := .Type()
	 := make([]reflect.Value, 0, .NumField())
	for  := 0;  < .NumField(); ++ {
		 := .Field()
		if .IsExported() {
			 = append(, .Field())
		}
	}

	return 
}

func ( any) ( WrappedEncodePlanNextSetter,  any,  bool) {
	if ,  := .(driver.Valuer);  {
		return nil, nil, false
	}

	// Avoid using reflect path for common types.
	switch value := .(type) {
	case []int16:
		return &wrapSliceEncodePlan[int16]{}, (FlatArray[int16])(), true
	case []int32:
		return &wrapSliceEncodePlan[int32]{}, (FlatArray[int32])(), true
	case []int64:
		return &wrapSliceEncodePlan[int64]{}, (FlatArray[int64])(), true
	case []float32:
		return &wrapSliceEncodePlan[float32]{}, (FlatArray[float32])(), true
	case []float64:
		return &wrapSliceEncodePlan[float64]{}, (FlatArray[float64])(), true
	case []string:
		return &wrapSliceEncodePlan[string]{}, (FlatArray[string])(), true
	case []time.Time:
		return &wrapSliceEncodePlan[time.Time]{}, (FlatArray[time.Time])(), true
	}

	if  := reflect.TypeOf();  != nil && .Kind() == reflect.Slice {
		 := anySliceArrayReflect{
			slice: reflect.ValueOf(),
		}
		return &wrapSliceEncodeReflectPlan{}, , true
	}

	return nil, nil, false
}

type wrapSliceEncodePlan[ any] struct {
	next EncodePlan
}

func ( *wrapSliceEncodePlan[]) ( EncodePlan) { .next =  }

func ( *wrapSliceEncodePlan[]) ( any,  []byte) ( []byte,  error) {
	return .next.Encode((FlatArray[])(.([])), )
}

type wrapSliceEncodeReflectPlan struct {
	next EncodePlan
}

func ( *wrapSliceEncodeReflectPlan) ( EncodePlan) { .next =  }

func ( *wrapSliceEncodeReflectPlan) ( any,  []byte) ( []byte,  error) {
	 := anySliceArrayReflect{
		slice: reflect.ValueOf(),
	}

	return .next.Encode(, )
}

func ( any) ( WrappedEncodePlanNextSetter,  any,  bool) {
	if ,  := .(driver.Valuer);  {
		return nil, nil, false
	}

	 := reflect.ValueOf()
	if .Kind() == reflect.Slice {
		 := .Type().Elem()

		if .Kind() == reflect.Slice {
			if !isRagged() {
				 := anyMultiDimSliceArray{
					slice: reflect.ValueOf(),
				}
				return &wrapMultiDimSliceEncodePlan{}, &, true
			}
		}
	}

	return nil, nil, false
}

type wrapMultiDimSliceEncodePlan struct {
	next EncodePlan
}

func ( *wrapMultiDimSliceEncodePlan) ( EncodePlan) { .next =  }

func ( *wrapMultiDimSliceEncodePlan) ( any,  []byte) ( []byte,  error) {
	 := anyMultiDimSliceArray{
		slice: reflect.ValueOf(),
	}

	return .next.Encode(&, )
}

func ( any) ( WrappedEncodePlanNextSetter,  any,  bool) {
	if ,  := .(driver.Valuer);  {
		return nil, nil, false
	}

	if  := reflect.TypeOf();  != nil && .Kind() == reflect.Array {
		 := anyArrayArrayReflect{
			array: reflect.ValueOf(),
		}
		return &wrapArrayEncodeReflectPlan{}, , true
	}

	return nil, nil, false
}

type wrapArrayEncodeReflectPlan struct {
	next EncodePlan
}

func ( *wrapArrayEncodeReflectPlan) ( EncodePlan) { .next =  }

func ( *wrapArrayEncodeReflectPlan) ( any,  []byte) ( []byte,  error) {
	 := anyArrayArrayReflect{
		array: reflect.ValueOf(),
	}

	return .next.Encode(, )
}

func newEncodeError( any,  *Map,  uint32,  int16,  error) error {
	var  string
	switch  {
	case TextFormatCode:
		 = "text"
	case BinaryFormatCode:
		 = "binary"
	default:
		 = fmt.Sprintf("unknown (%d)", )
	}

	var  string
	if ,  := .TypeForOID();  {
		 = .Name
	} else {
		 = "unknown type"
	}

	return fmt.Errorf("unable to encode %#v into %s format for %s (OID %d): %w", , , , , )
}

// Encode appends the encoded bytes of value to buf. If value is the SQL value NULL then append nothing and return
// (nil, nil). The caller of Encode is responsible for writing the correct NULL value or the length of the data
// written.
func ( *Map) ( uint32,  int16,  any,  []byte) ( []byte,  error) {
	if  == nil {
		return nil, nil
	}

	 := .PlanEncode(, , )
	if  == nil {
		return nil, newEncodeError(, , , , errors.New("cannot find encode plan"))
	}

	,  = .Encode(, )
	if  != nil {
		return nil, newEncodeError(, , , , )
	}

	return , nil
}

// SQLScanner returns a database/sql.Scanner for v. This is necessary for types like Array[T] and Range[T] where the
// type needs assistance from Map to implement the sql.Scanner interface. It is not necessary for types like Box that
// implement sql.Scanner directly.
//
// This uses the type of v to look up the PostgreSQL OID that v presumably came from. This means v must be registered
// with m by calling RegisterDefaultPgType.
func ( *Map) ( any) sql.Scanner {
	if ,  := .(sql.Scanner);  {
		return 
	}

	return &sqlScannerWrapper{m: , v: }
}

type sqlScannerWrapper struct {
	m *Map
	v any
}

func ( *sqlScannerWrapper) ( any) error {
	,  := .m.TypeForValue(.v)
	if ! {
		return fmt.Errorf("cannot convert to sql.Scanner: cannot find registered type for %T", .v)
	}

	var  []byte
	if  != nil {
		switch src := .(type) {
		case string:
			 = []byte()
		case []byte:
			 = 
		default:
			 = []byte(fmt.Sprint())
		}
	}

	return .m.Scan(.OID, TextFormatCode, , .v)
}