def x_upper_limit(self, limit=None):
        """Returns or sets (if a value is provided) the value at which the
        x-axis should end. By default this is the highest x value in the
        associated series.

        :param limit: If given, the chart's x_upper_limit will be set to this.
        :raises ValueError: if you try to make the upper limit smaller than the\
        lower limit."""

        if limit is None:
            if self._x_upper_limit is None:
                if self.smallest_x() == self.largest_x():
                    if int(self.largest_x()) == float(self.largest_x()):
                        return self.largest_x() + 1
                    else:
                        return math.ceil(self.largest_x())
                else:
                    return self.largest_x()
            else:
                return self._x_upper_limit
        else:
            if not is_numeric(limit):
                raise TypeError(
                 "upper x limit must be numeric, not '%s'" % str(limit)
                )
            if limit <= self.smallest_x():
                raise ValueError(
                 "upper x limit must be greater than lower limit (%s), not %s" % (
                  str(self.smallest_x()), str(limit)
                 )
                )
            self._x_upper_limit = limit