From c8ce6e9fe447204d8a6bce305002d0ec5b388f40 Mon Sep 17 00:00:00 2001
From: Anton Nikiforov <an.nikiforov@yadro.com>
Date: Thu, 4 Apr 2024 11:05:25 +0300
Subject: [PATCH] [#1072] node, ir: Add new config option
 `kludge_compatibility_mode`

Signed-off-by: Anton Nikiforov <an.nikiforov@yadro.com>
---
 cmd/frostfs-ir/config.go               |  1 +
 cmd/frostfs-ir/defaults.go             |  2 ++
 cmd/frostfs-ir/main.go                 |  6 +++++-
 cmd/frostfs-node/config.go             | 12 +++++++++++-
 cmd/frostfs-node/config/node/config.go |  5 +++++
 pkg/innerring/innerring.go             |  5 ++++-
 6 files changed, 28 insertions(+), 3 deletions(-)

diff --git a/cmd/frostfs-ir/config.go b/cmd/frostfs-ir/config.go
index be870052c..c73b68eb5 100644
--- a/cmd/frostfs-ir/config.go
+++ b/cmd/frostfs-ir/config.go
@@ -34,6 +34,7 @@ func reloadConfig() error {
 	if err != nil {
 		return err
 	}
+	cmode.Store(cfg.GetBool("node.kludge_compatibility_mode"))
 	err = logPrm.SetLevelString(cfg.GetString("logger.level"))
 	if err != nil {
 		return err
diff --git a/cmd/frostfs-ir/defaults.go b/cmd/frostfs-ir/defaults.go
index 127a68b29..23a475591 100644
--- a/cmd/frostfs-ir/defaults.go
+++ b/cmd/frostfs-ir/defaults.go
@@ -43,6 +43,8 @@ func defaultConfiguration(cfg *viper.Viper) {
 	setControlDefaults(cfg)
 
 	cfg.SetDefault("governance.disable", false)
+
+	cfg.SetDefault("node.kludge_compatibility_mode", false)
 }
 
 func setControlDefaults(cfg *viper.Viper) {
diff --git a/cmd/frostfs-ir/main.go b/cmd/frostfs-ir/main.go
index 9879342b7..31390dd74 100644
--- a/cmd/frostfs-ir/main.go
+++ b/cmd/frostfs-ir/main.go
@@ -6,6 +6,7 @@ import (
 	"fmt"
 	"os"
 	"sync"
+	"sync/atomic"
 
 	"git.frostfs.info/TrueCloudLab/frostfs-node/internal/logs"
 	"git.frostfs.info/TrueCloudLab/frostfs-node/misc"
@@ -37,6 +38,7 @@ var (
 	cfg        *viper.Viper
 	configFile *string
 	configDir  *string
+	cmode      = &atomic.Bool{}
 )
 
 func exitErr(err error) {
@@ -62,6 +64,8 @@ func main() {
 	cfg, err = newConfig()
 	exitErr(err)
 
+	cmode.Store(cfg.GetBool("node.kludge_compatibility_mode"))
+
 	metrics := irMetrics.NewInnerRingMetrics()
 
 	err = logPrm.SetLevelString(
@@ -84,7 +88,7 @@ func main() {
 	metricsCmp = newMetricsComponent()
 	metricsCmp.init()
 
-	innerRing, err = innerring.New(ctx, log, cfg, intErr, metrics)
+	innerRing, err = innerring.New(ctx, log, cfg, intErr, metrics, cmode)
 	exitErr(err)
 
 	pprofCmp.start()
diff --git a/cmd/frostfs-node/config.go b/cmd/frostfs-node/config.go
index 45ef771f3..d78a90cfc 100644
--- a/cmd/frostfs-node/config.go
+++ b/cmd/frostfs-node/config.go
@@ -109,6 +109,9 @@ type applicationConfiguration struct {
 		lowMem         bool
 		rebuildWorkers uint32
 	}
+
+	// if need to run node in compatibility with other versions mode
+	cmode *atomic.Bool
 }
 
 type shardCfg struct {
@@ -204,10 +207,13 @@ func (a *applicationConfiguration) readConfig(c *config.Config) error {
 		}
 
 		// clear if it is rereading
+		cmode := a.cmode
 		*a = applicationConfiguration{}
+		a.cmode = cmode
 	}
 
 	a._read = true
+	a.cmode.Store(nodeconfig.CompatibilityMode(c))
 
 	// Logger
 
@@ -648,7 +654,11 @@ type cfgControlService struct {
 var persistateSideChainLastBlockKey = []byte("side_chain_last_processed_block")
 
 func initCfg(appCfg *config.Config) *cfg {
-	c := &cfg{}
+	c := &cfg{
+		applicationConfiguration: applicationConfiguration{
+			cmode: &atomic.Bool{},
+		},
+	}
 
 	err := c.readConfig(appCfg)
 	if err != nil {
diff --git a/cmd/frostfs-node/config/node/config.go b/cmd/frostfs-node/config/node/config.go
index ac76ad47e..90338556e 100644
--- a/cmd/frostfs-node/config/node/config.go
+++ b/cmd/frostfs-node/config/node/config.go
@@ -292,3 +292,8 @@ func (l PersistentPolicyRulesConfig) Perm() fs.FileMode {
 func (l PersistentPolicyRulesConfig) NoSync() bool {
 	return config.BoolSafe((*config.Config)(l.cfg), "no_sync")
 }
+
+// CompatibilityMode returns true if need to run node in compatibility with previous versions mode.
+func CompatibilityMode(c *config.Config) bool {
+	return config.BoolSafe(c.Sub(subsection), "kludge_compatibility_mode")
+}
diff --git a/pkg/innerring/innerring.go b/pkg/innerring/innerring.go
index 5d7dc5a52..11d43f845 100644
--- a/pkg/innerring/innerring.go
+++ b/pkg/innerring/innerring.go
@@ -103,6 +103,8 @@ type (
 		// should report start errors
 		// to the application.
 		runners []func(chan<- error) error
+
+		cmode *atomic.Bool
 	}
 
 	chainParams struct {
@@ -330,12 +332,13 @@ func (s *Server) registerStarter(f func() error) {
 
 // New creates instance of inner ring sever structure.
 func New(ctx context.Context, log *logger.Logger, cfg *viper.Viper, errChan chan<- error,
-	metrics *metrics.InnerRingServiceMetrics,
+	metrics *metrics.InnerRingServiceMetrics, cmode *atomic.Bool,
 ) (*Server, error) {
 	var err error
 	server := &Server{
 		log:       log,
 		irMetrics: metrics,
+		cmode:     cmode,
 	}
 
 	server.sdNotify, err = server.initSdNotify(cfg)