code: function calcEnd(dir, schedArr, startsArr, startDate, maxEndDate) {
      var compare = compareFn(dir), result;
  
      for(var i = 0, len = schedArr.length; i < len; i++) {
        var start = startsArr[i];
  
        if(start && start.getTime() === startDate.getTime()) {
          var end = schedArr[i].end(dir, start);
  
          // if the end date is past the maxEndDate, just return the maxEndDate
          if(maxEndDate && (!end || compare(end, maxEndDate))) {
            return maxEndDate;
          }
  
          // otherwise, return the maximum end date that was calculated
          if(!result || compare(end, result)) {
            result = end;
          }
        }
      }
  
      return result;
    }
docs: Calculates the next invalid date for a particular schedules starting from
  the specified valid start date.
  
  @param {String} dir: The direction to use, either 'next' or 'prev'
  @param {Array} schedArr: The set of compiled schedules to use
  @param {Array} startsArr: The set of cached start dates for the schedules
  @param {Date} startDate: The valid date for which the end date will be found
  @param {Date} maxEndDate: The latested possible end date or null for none