@@ -11,6 +11,9 @@ import (
1111 "github.com/modern-go/reflect2"
1212)
1313
14+ // limit maximum depth of nesting, as allowed by https://tools.ietf.org/html/rfc7159#section-9
15+ const defaultMaxDepth = 10000
16+
1417// Config customize how the API should behave.
1518// The API is created from Config by Froze.
1619type Config struct {
@@ -25,6 +28,7 @@ type Config struct {
2528 ValidateJsonRawMessage bool
2629 ObjectFieldMustBeSimpleString bool
2730 CaseSensitive bool
31+ MaxDepth int
2832}
2933
3034// API the public interface of this package.
@@ -56,6 +60,7 @@ var ConfigCompatibleWithStandardLibrary = Config{
5660 EscapeHTML : true ,
5761 SortMapKeys : true ,
5862 ValidateJsonRawMessage : true ,
63+ MaxDepth : - 1 , // encoding/json has no max depth (stack overflow at 2581101)
5964}.Froze ()
6065
6166// ConfigFastest marshals float with only 6 digits precision
@@ -80,6 +85,7 @@ type frozenConfig struct {
8085 streamPool * sync.Pool
8186 iteratorPool * sync.Pool
8287 caseSensitive bool
88+ maxDepth int
8389}
8490
8591func (cfg * frozenConfig ) initCache () {
@@ -127,13 +133,17 @@ func addFrozenConfigToCache(cfg Config, frozenConfig *frozenConfig) {
127133
128134// Froze forge API from config
129135func (cfg Config ) Froze () API {
136+ if cfg .MaxDepth == 0 {
137+ cfg .MaxDepth = defaultMaxDepth
138+ }
130139 api := & frozenConfig {
131140 sortMapKeys : cfg .SortMapKeys ,
132141 indentionStep : cfg .IndentionStep ,
133142 objectFieldMustBeSimpleString : cfg .ObjectFieldMustBeSimpleString ,
134143 onlyTaggedField : cfg .OnlyTaggedField ,
135144 disallowUnknownFields : cfg .DisallowUnknownFields ,
136145 caseSensitive : cfg .CaseSensitive ,
146+ maxDepth : cfg .MaxDepth ,
137147 }
138148 api .streamPool = & sync.Pool {
139149 New : func () interface {} {
0 commit comments