@@ -246,7 +246,6 @@ type Generator struct {
246246 labels model.LabelSet
247247 rl atomic.Pointer [ratelimit.Limiter ]
248248 executionLoopOnce * sync.Once
249- executionLoopStart chan struct {}
250249 scheduleSegments []* Segment
251250 currentSegmentMu * sync.Mutex
252251 currentSegment * Segment
@@ -322,7 +321,6 @@ func NewGenerator(cfg *Config) (*Generator, error) {
322321 gun : cfg .Gun ,
323322 vu : cfg .VU ,
324323 executionLoopOnce : & sync.Once {},
325- executionLoopStart : make (chan struct {}),
326324 Responses : NewResponses (rch ),
327325 ResponsesChan : rch ,
328326 labels : ls ,
@@ -355,14 +353,10 @@ func NewGenerator(cfg *Config) (*Generator, error) {
355353// runRPSLoop initiates the generator's RPS loop, noop if load type is VU.
356354// It manages request pacing for RPS after the first segment is loaded.
357355func (g * Generator ) runRPSLoop () {
358- g .currentSegment = g .scheduleSegments [0 ]
359- g .stats .LastSegment .Store (int64 (len (g .scheduleSegments )))
360356 switch g .Cfg .LoadType {
361357 case RPS :
362358 g .ResponsesWaitGroup .Add (1 )
363359 // we run pacedCall controlled by stats.CurrentRPS
364- // start when first segment is loaded, see runScheduleLoop
365- <- g .executionLoopStart
366360 go func () {
367361 for {
368362 select {
@@ -491,9 +485,9 @@ func (g *Generator) processSegment() bool {
491485 newRateLimit := ratelimit .New (int (g .currentSegment .From ), ratelimit .Per (g .Cfg .RateLimitUnitDuration ), ratelimit .WithoutSlack )
492486 g .rl .Store (& newRateLimit )
493487 g .stats .CurrentRPS .Store (g .currentSegment .From )
494- // signal RPS loop to start
488+ // start RPS loop once, in next segments we control it using g.rl ratelimiter
495489 g .executionLoopOnce .Do (func () {
496- g .executionLoopStart <- struct {}{}
490+ g .runRPSLoop ()
497491 })
498492 case VU :
499493 oldVUs := g .stats .CurrentVUs .Load ()
@@ -524,6 +518,8 @@ func (g *Generator) processSegment() bool {
524518// runScheduleLoop initiates an asynchronous loop that processes scheduling segments and monitors for completion signals.
525519// It enables the generator to handle load distribution seamlessly in the background.
526520func (g * Generator ) runScheduleLoop () {
521+ g .currentSegment = g .scheduleSegments [0 ]
522+ g .stats .LastSegment .Store (int64 (len (g .scheduleSegments )))
527523 go func () {
528524 for {
529525 select {
@@ -661,7 +657,6 @@ func (g *Generator) Run(wait bool) (interface{}, bool) {
661657 g .sendStatsToLoki ()
662658 }
663659 g .runScheduleLoop ()
664- g .runRPSLoop ()
665660 g .collectVUResults ()
666661 if wait {
667662 return g .Wait ()
0 commit comments