code: func checkCreatePartitionValue(ctx sessionctx.Context, tblInfo *model.TableInfo, pi *model.PartitionInfo, cols []*table.Column) error {
  	defs := pi.Definitions
  	if len(defs) <= 1 {
  		return nil
  	}
  
  	if strings.EqualFold(defs[len(defs)-1].LessThan[0], partitionMaxValue) {
  		defs = defs[:len(defs)-1]
  	}
  	isUnsignedBigint := isRangePartitionColUnsignedBigint(cols, pi)
  	var prevRangeValue interface{}
  	for i := 0; i < len(defs); i++ {
  		if strings.EqualFold(defs[i].LessThan[0], partitionMaxValue) {
  			return errors.Trace(ErrPartitionMaxvalue)
  		}
  
  		currentRangeValue, fromExpr, err := getRangeValue(ctx, tblInfo, defs[i].LessThan[0], isUnsignedBigint)
  		if err != nil {
  			return errors.Trace(err)
  		}
  		if fromExpr {
  			// Constant fold the expression.
  			defs[i].LessThan[0] = fmt.Sprintf("%d", currentRangeValue)
  		}
  
  		if i == 0 {
  			prevRangeValue = currentRangeValue
  			continue
  		}
  
  		if isUnsignedBigint {
  			if currentRangeValue.(uint64) <= prevRangeValue.(uint64) {
  				return errors.Trace(ErrRangeNotIncreasing)
  			}
  		} else {
  			if currentRangeValue.(int64) <= prevRangeValue.(int64) {
  				return errors.Trace(ErrRangeNotIncreasing)
  			}
  		}
  		prevRangeValue = currentRangeValue
  	}
  	return nil
  }
docs: // checkCreatePartitionValue checks whether `less than value` is strictly increasing for each partition.
  // Side effect: it may simplify the partition range definition from a constant expression to an integer.