mirror of
				https://github.com/redis/go-redis.git
				synced 2025-11-04 02:33:24 +03:00 
			
		
		
		
	fix: handle network error on SETINFO (#3295) (CVE-2025-29923)
* fix: handle network error on SETINFO This fix addresses potential out of order responses as described in `CVE-2025-29923` * fix: deprecate DisableIndentity and introduce DisableIdentity Both options will work before V10. In v10 DisableIndentity will be dropped. The preferred flag to use is `DisableIdentity`.
This commit is contained in:
		@@ -169,16 +169,18 @@ By default, go-redis automatically sends the client library name and version dur
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
#### Disabling Identity Verification
 | 
					#### Disabling Identity Verification
 | 
				
			||||||
 | 
					
 | 
				
			||||||
When connection identity verification is not required or needs to be explicitly disabled, a `DisableIndentity` configuration option exists. In V10 of this library, `DisableIndentity` will become `DisableIdentity` in order to fix the associated typo.
 | 
					When connection identity verification is not required or needs to be explicitly disabled, a `DisableIdentity` configuration option exists.
 | 
				
			||||||
 | 
					Initially there was a typo and the option was named `DisableIndentity` instead of `DisableIdentity`. The misspelled option is marked as Deprecated and will be removed in V10 of this library.
 | 
				
			||||||
 | 
					Although both options will work at the moment, the correct option is `DisableIdentity`. The deprecated option will be removed in V10 of this library, so please use the correct option name to avoid any issues.
 | 
				
			||||||
 | 
					
 | 
				
			||||||
To disable verification, set the `DisableIndentity` option to `true` in the Redis client options:
 | 
					To disable verification, set the `DisableIdentity` option to `true` in the Redis client options:
 | 
				
			||||||
 | 
					
 | 
				
			||||||
```go
 | 
					```go
 | 
				
			||||||
rdb := redis.NewClient(&redis.Options{
 | 
					rdb := redis.NewClient(&redis.Options{
 | 
				
			||||||
    Addr:            "localhost:6379",
 | 
					    Addr:            "localhost:6379",
 | 
				
			||||||
    Password:        "",
 | 
					    Password:        "",
 | 
				
			||||||
    DB:              0,
 | 
					    DB:              0,
 | 
				
			||||||
    DisableIndentity: true, // Disable set-info on connect
 | 
					    DisableIdentity: true, // Disable set-info on connect
 | 
				
			||||||
})
 | 
					})
 | 
				
			||||||
```
 | 
					```
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -30,7 +30,7 @@ func NewClientStub(resp []byte) *ClientStub {
 | 
				
			|||||||
		Dialer: func(ctx context.Context, network, addr string) (net.Conn, error) {
 | 
							Dialer: func(ctx context.Context, network, addr string) (net.Conn, error) {
 | 
				
			||||||
			return stub.stubConn(initHello), nil
 | 
								return stub.stubConn(initHello), nil
 | 
				
			||||||
		},
 | 
							},
 | 
				
			||||||
		DisableIndentity: true,
 | 
							DisableIdentity: true,
 | 
				
			||||||
	})
 | 
						})
 | 
				
			||||||
	return stub
 | 
						return stub
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
@@ -46,7 +46,7 @@ func NewClusterClientStub(resp []byte) *ClientStub {
 | 
				
			|||||||
		Dialer: func(ctx context.Context, network, addr string) (net.Conn, error) {
 | 
							Dialer: func(ctx context.Context, network, addr string) (net.Conn, error) {
 | 
				
			||||||
			return stub.stubConn(initHello), nil
 | 
								return stub.stubConn(initHello), nil
 | 
				
			||||||
		},
 | 
							},
 | 
				
			||||||
		DisableIndentity: true,
 | 
							DisableIdentity: true,
 | 
				
			||||||
 | 
					
 | 
				
			||||||
		ClusterSlots: func(_ context.Context) ([]ClusterSlot, error) {
 | 
							ClusterSlots: func(_ context.Context) ([]ClusterSlot, error) {
 | 
				
			||||||
			return []ClusterSlot{
 | 
								return []ClusterSlot{
 | 
				
			||||||
 
 | 
				
			|||||||
							
								
								
									
										11
									
								
								options.go
									
									
									
									
									
								
							
							
						
						
									
										11
									
								
								options.go
									
									
									
									
									
								
							@@ -148,9 +148,18 @@ type Options struct {
 | 
				
			|||||||
	// Enables read only queries on slave/follower nodes.
 | 
						// Enables read only queries on slave/follower nodes.
 | 
				
			||||||
	readOnly bool
 | 
						readOnly bool
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	// Disable set-lib on connect. Default is false.
 | 
						// DisableIndentity - Disable set-lib on connect.
 | 
				
			||||||
 | 
						//
 | 
				
			||||||
 | 
						// default: false
 | 
				
			||||||
 | 
						//
 | 
				
			||||||
 | 
						// Deprecated: Use DisableIdentity instead.
 | 
				
			||||||
	DisableIndentity bool
 | 
						DisableIndentity bool
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						// DisableIdentity is used to disable CLIENT SETINFO command on connect.
 | 
				
			||||||
 | 
						//
 | 
				
			||||||
 | 
						// default: false
 | 
				
			||||||
 | 
						DisableIdentity bool
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	// Add suffix to client name. Default is empty.
 | 
						// Add suffix to client name. Default is empty.
 | 
				
			||||||
	IdentitySuffix string
 | 
						IdentitySuffix string
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -86,8 +86,19 @@ type ClusterOptions struct {
 | 
				
			|||||||
	ConnMaxIdleTime time.Duration
 | 
						ConnMaxIdleTime time.Duration
 | 
				
			||||||
	ConnMaxLifetime time.Duration
 | 
						ConnMaxLifetime time.Duration
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	TLSConfig        *tls.Config
 | 
						TLSConfig *tls.Config
 | 
				
			||||||
	DisableIndentity bool // Disable set-lib on connect. Default is false.
 | 
					
 | 
				
			||||||
 | 
						// DisableIndentity - Disable set-lib on connect.
 | 
				
			||||||
 | 
						//
 | 
				
			||||||
 | 
						// default: false
 | 
				
			||||||
 | 
						//
 | 
				
			||||||
 | 
						// Deprecated: Use DisableIdentity instead.
 | 
				
			||||||
 | 
						DisableIndentity bool
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						// DisableIdentity is used to disable CLIENT SETINFO command on connect.
 | 
				
			||||||
 | 
						//
 | 
				
			||||||
 | 
						// default: false
 | 
				
			||||||
 | 
						DisableIdentity bool
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	IdentitySuffix string // Add suffix to client name. Default is empty.
 | 
						IdentitySuffix string // Add suffix to client name. Default is empty.
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
@@ -296,7 +307,8 @@ func (opt *ClusterOptions) clientOptions() *Options {
 | 
				
			|||||||
		MaxActiveConns:   opt.MaxActiveConns,
 | 
							MaxActiveConns:   opt.MaxActiveConns,
 | 
				
			||||||
		ConnMaxIdleTime:  opt.ConnMaxIdleTime,
 | 
							ConnMaxIdleTime:  opt.ConnMaxIdleTime,
 | 
				
			||||||
		ConnMaxLifetime:  opt.ConnMaxLifetime,
 | 
							ConnMaxLifetime:  opt.ConnMaxLifetime,
 | 
				
			||||||
		DisableIndentity: opt.DisableIndentity,
 | 
							DisableIdentity:  opt.DisableIdentity,
 | 
				
			||||||
 | 
							DisableIndentity: opt.DisableIdentity,
 | 
				
			||||||
		IdentitySuffix:   opt.IdentitySuffix,
 | 
							IdentitySuffix:   opt.IdentitySuffix,
 | 
				
			||||||
		TLSConfig:        opt.TLSConfig,
 | 
							TLSConfig:        opt.TLSConfig,
 | 
				
			||||||
		// If ClusterSlots is populated, then we probably have an artificial
 | 
							// If ClusterSlots is populated, then we probably have an artificial
 | 
				
			||||||
 
 | 
				
			|||||||
							
								
								
									
										8
									
								
								redis.go
									
									
									
									
									
								
							
							
						
						
									
										8
									
								
								redis.go
									
									
									
									
									
								
							@@ -345,7 +345,7 @@ func (c *baseClient) initConn(ctx context.Context, cn *pool.Conn) error {
 | 
				
			|||||||
		return err
 | 
							return err
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	if !c.opt.DisableIndentity {
 | 
						if !c.opt.DisableIdentity && !c.opt.DisableIndentity {
 | 
				
			||||||
		libName := ""
 | 
							libName := ""
 | 
				
			||||||
		libVer := Version()
 | 
							libVer := Version()
 | 
				
			||||||
		if c.opt.IdentitySuffix != "" {
 | 
							if c.opt.IdentitySuffix != "" {
 | 
				
			||||||
@@ -354,7 +354,11 @@ func (c *baseClient) initConn(ctx context.Context, cn *pool.Conn) error {
 | 
				
			|||||||
		p := conn.Pipeline()
 | 
							p := conn.Pipeline()
 | 
				
			||||||
		p.ClientSetInfo(ctx, WithLibraryName(libName))
 | 
							p.ClientSetInfo(ctx, WithLibraryName(libName))
 | 
				
			||||||
		p.ClientSetInfo(ctx, WithLibraryVersion(libVer))
 | 
							p.ClientSetInfo(ctx, WithLibraryVersion(libVer))
 | 
				
			||||||
		_, _ = p.Exec(ctx)
 | 
							// Handle network errors (e.g. timeouts) in CLIENT SETINFO to avoid
 | 
				
			||||||
 | 
							// out of order responses later on.
 | 
				
			||||||
 | 
							if _, err = p.Exec(ctx); err != nil && !isRedisError(err) {
 | 
				
			||||||
 | 
								return err
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	if c.opt.OnConnect != nil {
 | 
						if c.opt.OnConnect != nil {
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -373,6 +373,13 @@ var _ = Describe("Client timeout", func() {
 | 
				
			|||||||
	})
 | 
						})
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	testTimeout := func() {
 | 
						testTimeout := func() {
 | 
				
			||||||
 | 
							It("SETINFO timeouts", func() {
 | 
				
			||||||
 | 
								conn := client.Conn()
 | 
				
			||||||
 | 
								err := conn.Ping(ctx).Err()
 | 
				
			||||||
 | 
								Expect(err).To(HaveOccurred())
 | 
				
			||||||
 | 
								Expect(err.(net.Error).Timeout()).To(BeTrue())
 | 
				
			||||||
 | 
							})
 | 
				
			||||||
 | 
					
 | 
				
			||||||
		It("Ping timeouts", func() {
 | 
							It("Ping timeouts", func() {
 | 
				
			||||||
			err := client.Ping(ctx).Err()
 | 
								err := client.Ping(ctx).Err()
 | 
				
			||||||
			Expect(err).To(HaveOccurred())
 | 
								Expect(err).To(HaveOccurred())
 | 
				
			||||||
 
 | 
				
			|||||||
							
								
								
									
										13
									
								
								ring.go
									
									
									
									
									
								
							
							
						
						
									
										13
									
								
								ring.go
									
									
									
									
									
								
							@@ -98,8 +98,18 @@ type RingOptions struct {
 | 
				
			|||||||
	TLSConfig *tls.Config
 | 
						TLSConfig *tls.Config
 | 
				
			||||||
	Limiter   Limiter
 | 
						Limiter   Limiter
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						// DisableIndentity - Disable set-lib on connect.
 | 
				
			||||||
 | 
						//
 | 
				
			||||||
 | 
						// default: false
 | 
				
			||||||
 | 
						//
 | 
				
			||||||
 | 
						// Deprecated: Use DisableIdentity instead.
 | 
				
			||||||
	DisableIndentity bool
 | 
						DisableIndentity bool
 | 
				
			||||||
	IdentitySuffix   string
 | 
					
 | 
				
			||||||
 | 
						// DisableIdentity is used to disable CLIENT SETINFO command on connect.
 | 
				
			||||||
 | 
						//
 | 
				
			||||||
 | 
						// default: false
 | 
				
			||||||
 | 
						DisableIdentity bool
 | 
				
			||||||
 | 
						IdentitySuffix  string
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
func (opt *RingOptions) init() {
 | 
					func (opt *RingOptions) init() {
 | 
				
			||||||
@@ -166,6 +176,7 @@ func (opt *RingOptions) clientOptions() *Options {
 | 
				
			|||||||
		TLSConfig: opt.TLSConfig,
 | 
							TLSConfig: opt.TLSConfig,
 | 
				
			||||||
		Limiter:   opt.Limiter,
 | 
							Limiter:   opt.Limiter,
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
							DisableIdentity:  opt.DisableIdentity,
 | 
				
			||||||
		DisableIndentity: opt.DisableIndentity,
 | 
							DisableIndentity: opt.DisableIndentity,
 | 
				
			||||||
		IdentitySuffix:   opt.IdentitySuffix,
 | 
							IdentitySuffix:   opt.IdentitySuffix,
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
 
 | 
				
			|||||||
							
								
								
									
										16
									
								
								sentinel.go
									
									
									
									
									
								
							
							
						
						
									
										16
									
								
								sentinel.go
									
									
									
									
									
								
							@@ -80,8 +80,19 @@ type FailoverOptions struct {
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
	TLSConfig *tls.Config
 | 
						TLSConfig *tls.Config
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						// DisableIndentity - Disable set-lib on connect.
 | 
				
			||||||
 | 
						//
 | 
				
			||||||
 | 
						// default: false
 | 
				
			||||||
 | 
						//
 | 
				
			||||||
 | 
						// Deprecated: Use DisableIdentity instead.
 | 
				
			||||||
	DisableIndentity bool
 | 
						DisableIndentity bool
 | 
				
			||||||
	IdentitySuffix   string
 | 
					
 | 
				
			||||||
 | 
						// DisableIdentity is used to disable CLIENT SETINFO command on connect.
 | 
				
			||||||
 | 
						//
 | 
				
			||||||
 | 
						// default: false
 | 
				
			||||||
 | 
						DisableIdentity bool
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						IdentitySuffix string
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
func (opt *FailoverOptions) clientOptions() *Options {
 | 
					func (opt *FailoverOptions) clientOptions() *Options {
 | 
				
			||||||
@@ -117,6 +128,7 @@ func (opt *FailoverOptions) clientOptions() *Options {
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
		TLSConfig: opt.TLSConfig,
 | 
							TLSConfig: opt.TLSConfig,
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
							DisableIdentity:  opt.DisableIdentity,
 | 
				
			||||||
		DisableIndentity: opt.DisableIndentity,
 | 
							DisableIndentity: opt.DisableIndentity,
 | 
				
			||||||
		IdentitySuffix:   opt.IdentitySuffix,
 | 
							IdentitySuffix:   opt.IdentitySuffix,
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
@@ -154,6 +166,7 @@ func (opt *FailoverOptions) sentinelOptions(addr string) *Options {
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
		TLSConfig: opt.TLSConfig,
 | 
							TLSConfig: opt.TLSConfig,
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
							DisableIdentity:  opt.DisableIdentity,
 | 
				
			||||||
		DisableIndentity: opt.DisableIndentity,
 | 
							DisableIndentity: opt.DisableIndentity,
 | 
				
			||||||
		IdentitySuffix:   opt.IdentitySuffix,
 | 
							IdentitySuffix:   opt.IdentitySuffix,
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
@@ -194,6 +207,7 @@ func (opt *FailoverOptions) clusterOptions() *ClusterOptions {
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
		TLSConfig: opt.TLSConfig,
 | 
							TLSConfig: opt.TLSConfig,
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
							DisableIdentity:  opt.DisableIdentity,
 | 
				
			||||||
		DisableIndentity: opt.DisableIndentity,
 | 
							DisableIndentity: opt.DisableIndentity,
 | 
				
			||||||
		IdentitySuffix:   opt.IdentitySuffix,
 | 
							IdentitySuffix:   opt.IdentitySuffix,
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
 
 | 
				
			|||||||
							
								
								
									
										17
									
								
								universal.go
									
									
									
									
									
								
							
							
						
						
									
										17
									
								
								universal.go
									
									
									
									
									
								
							@@ -66,8 +66,19 @@ type UniversalOptions struct {
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
	MasterName string
 | 
						MasterName string
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						// DisableIndentity - Disable set-lib on connect.
 | 
				
			||||||
 | 
						//
 | 
				
			||||||
 | 
						// default: false
 | 
				
			||||||
 | 
						//
 | 
				
			||||||
 | 
						// Deprecated: Use DisableIdentity instead.
 | 
				
			||||||
	DisableIndentity bool
 | 
						DisableIndentity bool
 | 
				
			||||||
	IdentitySuffix   string
 | 
					
 | 
				
			||||||
 | 
						// DisableIdentity is used to disable CLIENT SETINFO command on connect.
 | 
				
			||||||
 | 
						//
 | 
				
			||||||
 | 
						// default: false
 | 
				
			||||||
 | 
						DisableIdentity bool
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						IdentitySuffix string
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// Cluster returns cluster options created from the universal options.
 | 
					// Cluster returns cluster options created from the universal options.
 | 
				
			||||||
@@ -112,6 +123,7 @@ func (o *UniversalOptions) Cluster() *ClusterOptions {
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
		TLSConfig: o.TLSConfig,
 | 
							TLSConfig: o.TLSConfig,
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
							DisableIdentity:  o.DisableIdentity,
 | 
				
			||||||
		DisableIndentity: o.DisableIndentity,
 | 
							DisableIndentity: o.DisableIndentity,
 | 
				
			||||||
		IdentitySuffix:   o.IdentitySuffix,
 | 
							IdentitySuffix:   o.IdentitySuffix,
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
@@ -158,6 +170,8 @@ func (o *UniversalOptions) Failover() *FailoverOptions {
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
		TLSConfig: o.TLSConfig,
 | 
							TLSConfig: o.TLSConfig,
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
							DisableIdentity:  o.DisableIdentity,
 | 
				
			||||||
		DisableIndentity: o.DisableIndentity,
 | 
							DisableIndentity: o.DisableIndentity,
 | 
				
			||||||
		IdentitySuffix:   o.IdentitySuffix,
 | 
							IdentitySuffix:   o.IdentitySuffix,
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
@@ -201,6 +215,7 @@ func (o *UniversalOptions) Simple() *Options {
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
		TLSConfig: o.TLSConfig,
 | 
							TLSConfig: o.TLSConfig,
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
							DisableIdentity:  o.DisableIdentity,
 | 
				
			||||||
		DisableIndentity: o.DisableIndentity,
 | 
							DisableIndentity: o.DisableIndentity,
 | 
				
			||||||
		IdentitySuffix:   o.IdentitySuffix,
 | 
							IdentitySuffix:   o.IdentitySuffix,
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
 
 | 
				
			|||||||
		Reference in New Issue
	
	Block a user