You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@xalan.apache.org by mu...@apache.org on 2023/08/30 12:47:13 UTC

[xalan-java] branch xalan-j_xslt3.0 updated: committing improvements to the use of xml schema data types xs:duration, xs:yearMonthDuration, xs:dayTimeDuration within xpath 3.1 implementation. also committing improvements to the implementation of xpath 3.1 functions fn:max, fn:min when using the xml schema data types xs:yearMonthDuration, xs:dayTimeDuration. also committing few new working related test cases as well.

This is an automated email from the ASF dual-hosted git repository.

mukulg pushed a commit to branch xalan-j_xslt3.0
in repository https://gitbox.apache.org/repos/asf/xalan-java.git


The following commit(s) were added to refs/heads/xalan-j_xslt3.0 by this push:
     new c7217abe committing improvements to the use of xml schema data types xs:duration, xs:yearMonthDuration, xs:dayTimeDuration within xpath 3.1 implementation. also committing improvements to the implementation of xpath 3.1 functions fn:max, fn:min when using the xml schema data types xs:yearMonthDuration, xs:dayTimeDuration. also committing few new working related test cases as well.
     new 04989dd9 Merge pull request #70 from mukulga/xalan-j_xslt3.0_mukul
c7217abe is described below

commit c7217abe8842d475e358374657328fc4291d24d1
Author: Mukul Gandhi <ga...@gmail.com>
AuthorDate: Wed Aug 30 18:10:09 2023 +0530

    committing improvements to the use of xml schema data types xs:duration, xs:yearMonthDuration, xs:dayTimeDuration within xpath 3.1 implementation. also committing improvements to the implementation of xpath 3.1 functions fn:max, fn:min when using the xml schema data types xs:yearMonthDuration, xs:dayTimeDuration. also committing few new working related test cases as well.
---
 .../xalan/templates/XSConstructorFunctionUtil.java | 296 +++++++++++----------
 src/org/apache/xpath/compiler/Keywords.java        |   3 +
 src/org/apache/xpath/functions/FuncMax.java        |  68 ++++-
 src/org/apache/xpath/functions/FuncMin.java        |  70 ++++-
 .../apache/xpath/xs/types/XSDayTimeDuration.java   | 108 ++++++++
 src/org/apache/xpath/xs/types/XSDuration.java      | 128 +++++++--
 .../apache/xpath/xs/types/XSYearMonthDuration.java | 138 +++++++---
 tests/fn_max/gold/test3.out                        |   1 +
 tests/fn_max/gold/test4.out                        |   1 +
 tests/fn_max/gold/test5.out                        |   1 +
 tests/fn_max/test1_b.xml                           |   5 +
 tests/fn_max/test3.xsl                             |  47 ++++
 tests/fn_max/test4.xsl                             |  43 +++
 tests/fn_max/test5.xsl                             |  43 +++
 tests/fn_min/gold/test3.out                        |   1 +
 tests/fn_min/gold/test4.out                        |   1 +
 tests/fn_min/test3.xsl                             |  43 +++
 tests/fn_min/test4.xsl                             |  43 +++
 tests/fn_sort/gold/test16.out                      |  32 +++
 tests/fn_sort/test19.xsl                           |  57 ++++
 tests/fn_sort/test1_i.xml                          |  10 +
 tests/org/apache/xalan/xpath3/FnMaxTests.java      |  30 +++
 tests/org/apache/xalan/xpath3/FnMinTests.java      |  20 ++
 tests/org/apache/xalan/xpath3/FnSortTests.java     |  10 +
 24 files changed, 981 insertions(+), 218 deletions(-)

diff --git a/src/org/apache/xalan/templates/XSConstructorFunctionUtil.java b/src/org/apache/xalan/templates/XSConstructorFunctionUtil.java
index 2e44d4d9..be8e2a15 100644
--- a/src/org/apache/xalan/templates/XSConstructorFunctionUtil.java
+++ b/src/org/apache/xalan/templates/XSConstructorFunctionUtil.java
@@ -53,12 +53,9 @@ import org.xml.sax.SAXException;
  */
 public class XSConstructorFunctionUtil {
     
-    /*
-     * Process an XPath expression of the type FuncExtFunction, XPath operation, 
-     * and also few default XPath expression processing.
-     * 
-     * We use the XalanJ extension function evaluation mechanism, to evaluate
-     * XPath 3.1 constructor functions.
+    /**
+     * Process an XPath expression of type FuncExtFunction, XPath operation, 
+     * and also few XPath default expression processing.
      */
     public static XObject processFuncExtFunctionOrXPathOpn(XPathContext xctxt, Expression expr)
                                                                     throws TransformerException, SAXException {        
@@ -66,144 +63,175 @@ public class XSConstructorFunctionUtil {
         
         SourceLocator srcLocator = xctxt.getSAXLocator();
 
+        // XalanJ's extension function handler mechanism, treats at a syntactic level,
+        // XPath 3.1 constructor function calls like xs:type_name(..) as calls to XSLT/XPath
+        // extension functions. If the XML namespace of XSLT/XPath function calls is an XML Schema
+        // namespace, then we use this fact to treat such function calls as XPath 3.1 constructor 
+        // function calls, as has been implemented within code below.
+        
         if (expr instanceof FuncExtFunction) {
             FuncExtFunction funcExtFunction = (FuncExtFunction)expr;
+            
             if (XMLConstants.W3C_XML_SCHEMA_NS_URI.equals(funcExtFunction.getNamespace())) {
-                // evaluate XPath 3.1 constructor function calls, corresponding to XML Schema 
-                // built-in types.
+                // Handle as an XPath 3.1 constructor function call
                 
-                if ((Keywords.XS_STRING).equals(funcExtFunction.getFunctionName())) {                              
-                    ResultSequence argSequence = new ResultSequence();
-                    for (int idx = 0; idx < funcExtFunction.getArgCount(); idx++) {
-                        XObject argVal = (funcExtFunction.getArg(idx)).execute(xctxt);
-                        argSequence.add(new XSString(XslTransformEvaluationHelper.getStrVal(argVal)));
-                    }
-
-                    ResultSequence rSeq = (new XSString()).constructor(argSequence);
-                    evalResult = rSeq.item(0);              
-                }
-                else if ((Keywords.XS_DECIMAL).equals(funcExtFunction.getFunctionName())) {                              
-                    ResultSequence argSequence = new ResultSequence();
-                    for (int idx = 0; idx < funcExtFunction.getArgCount(); idx++) {
-                        XObject argVal = (funcExtFunction.getArg(idx)).execute(xctxt);
-                        argSequence.add(new XSDecimal(XslTransformEvaluationHelper.getStrVal(argVal)));
-                    }
-
-                    ResultSequence rSeq = (new XSDecimal()).constructor(argSequence);
-                    evalResult = rSeq.item(0);              
-                }
-                else if ((Keywords.XS_FLOAT).equals(funcExtFunction.getFunctionName())) {                              
-                    ResultSequence argSequence = new ResultSequence();
-                    for (int idx = 0; idx < funcExtFunction.getArgCount(); idx++) {
-                        XObject argVal = (funcExtFunction.getArg(idx)).execute(xctxt);
-                        argSequence.add(new XSFloat(XslTransformEvaluationHelper.getStrVal(argVal)));
-                    }
-
-                    ResultSequence rSeq = (new XSFloat()).constructor(argSequence);
-                    evalResult = rSeq.item(0);              
-                }
-                else if ((Keywords.XS_DOUBLE).equals(funcExtFunction.getFunctionName())) {                              
-                    ResultSequence argSequence = new ResultSequence();
-                    for (int idx = 0; idx < funcExtFunction.getArgCount(); idx++) {
-                        XObject argVal = (funcExtFunction.getArg(idx)).execute(xctxt);
-                        argSequence.add(new XSDouble(XslTransformEvaluationHelper.getStrVal(argVal)));
-                    }
-
-                    ResultSequence rSeq = (new XSDouble()).constructor(argSequence);
-                    evalResult = rSeq.item(0);              
-                }
-                else if ((Keywords.XS_INTEGER).equals(funcExtFunction.getFunctionName())) {                              
-                    ResultSequence argSequence = new ResultSequence();
-                    for (int idx = 0; idx < funcExtFunction.getArgCount(); idx++) {
-                        XObject argVal = (funcExtFunction.getArg(idx)).execute(xctxt);
-                        argSequence.add(new XSInteger(XslTransformEvaluationHelper.getStrVal(argVal)));
-                    }
-
-                    ResultSequence rSeq = (new XSInteger()).constructor(argSequence);
-                    evalResult = rSeq.item(0);              
-                }
-                else if ((Keywords.XS_LONG).equals(funcExtFunction.getFunctionName())) {                              
-                    ResultSequence argSequence = new ResultSequence();
-                    for (int idx = 0; idx < funcExtFunction.getArgCount(); idx++) {
-                        XObject argVal = (funcExtFunction.getArg(idx)).execute(xctxt);
-                        argSequence.add(new XSLong(XslTransformEvaluationHelper.getStrVal(argVal)));
-                    }
-
-                    ResultSequence rSeq = (new XSLong()).constructor(argSequence);
-                    evalResult = rSeq.item(0);              
-                }
-                else if ((Keywords.XS_INT).equals(funcExtFunction.getFunctionName())) {                              
-                    ResultSequence argSequence = new ResultSequence();
-                    for (int idx = 0; idx < funcExtFunction.getArgCount(); idx++) {
-                        XObject argVal = (funcExtFunction.getArg(idx)).execute(xctxt);
-                        argSequence.add(new XSInt(XslTransformEvaluationHelper.getStrVal(argVal)));
-                    }
-
-                    ResultSequence rSeq = (new XSInt()).constructor(argSequence);
-                    evalResult = rSeq.item(0);              
-                }
-                else if ((Keywords.FUNC_BOOLEAN_STRING).equals(funcExtFunction.getFunctionName())) {                              
-                    ResultSequence argSequence = new ResultSequence();
-                    for (int idx = 0; idx < funcExtFunction.getArgCount(); idx++) {
-                        XObject argVal = (funcExtFunction.getArg(idx)).execute(xctxt);
-                        Boolean boolVal = Boolean.valueOf("0".equals(XslTransformEvaluationHelper.getStrVal(argVal)) ? 
-                                                                                 "false" : "true");
-                        argSequence.add(new XSBoolean(boolVal));
-                    }
-
-                    ResultSequence rSeq = (new XSBoolean()).constructor(argSequence);
-                    evalResult = rSeq.item(0);              
-                }
-                else if ((Keywords.XS_DATE).equals(funcExtFunction.getFunctionName())) {                              
-                    ResultSequence argSequence = new ResultSequence();
-                    for (int idx = 0; idx < funcExtFunction.getArgCount(); idx++) {
-                        XObject argVal = (funcExtFunction.getArg(idx)).execute(xctxt);
-                        argSequence.add(XSDate.parseDate(XslTransformEvaluationHelper.getStrVal(argVal)));
-                    }
-
-                    ResultSequence rSeq = (new XSDate()).constructor(argSequence); 
-                    evalResult = rSeq.item(0);              
-                }
-                else if ((Keywords.XS_YEAR_MONTH_DURATION).equals(funcExtFunction.getFunctionName())) {                    
-                    for (int idx = 0; idx < funcExtFunction.getArgCount(); idx++) {
-                        XObject argVal = (funcExtFunction.getArg(idx)).execute(xctxt);
-                        String strVal = XslTransformEvaluationHelper.getStrVal(argVal);
-                        XSDuration xsDuration = XSYearMonthDuration.parseYearMonthDuration(strVal);
-                        if (xsDuration != null) {
-                           ResultSequence argSequence = new ResultSequence();
-                           argSequence.add(xsDuration);
-                           ResultSequence rSeq = (new XSYearMonthDuration()).constructor(argSequence); 
-                           evalResult = rSeq.item(0);
+                ResultSequence argSequence = new ResultSequence();
+                ResultSequence evalResultSequence = null;
+                
+                switch (funcExtFunction.getFunctionName()) {
+                    case Keywords.XS_STRING :                        
+                        for (int idx = 0; idx < funcExtFunction.getArgCount(); idx++) {
+                            XObject argVal = (funcExtFunction.getArg(idx)).execute(xctxt);
+                            argSequence.add(new XSString(XslTransformEvaluationHelper.getStrVal(argVal)));
+                        }
+    
+                        evalResultSequence = (new XSString()).constructor(argSequence);
+                        evalResult = evalResultSequence.item(0);
+                        
+                        break;
+                    case Keywords.XS_DECIMAL :
+                        for (int idx = 0; idx < funcExtFunction.getArgCount(); idx++) {
+                            XObject argVal = (funcExtFunction.getArg(idx)).execute(xctxt);
+                            argSequence.add(new XSDecimal(XslTransformEvaluationHelper.getStrVal(argVal)));
+                        }
+    
+                        evalResultSequence = (new XSDecimal()).constructor(argSequence);
+                        evalResult = evalResultSequence.item(0);
+                        
+                        break;
+                    case Keywords.XS_FLOAT :
+                        for (int idx = 0; idx < funcExtFunction.getArgCount(); idx++) {
+                            XObject argVal = (funcExtFunction.getArg(idx)).execute(xctxt);
+                            argSequence.add(new XSFloat(XslTransformEvaluationHelper.getStrVal(argVal)));
+                        }
+    
+                        evalResultSequence = (new XSFloat()).constructor(argSequence);
+                        evalResult = evalResultSequence.item(0);
+                        
+                        break;                
+                    case Keywords.XS_DOUBLE :
+                        for (int idx = 0; idx < funcExtFunction.getArgCount(); idx++) {
+                            XObject argVal = (funcExtFunction.getArg(idx)).execute(xctxt);
+                            argSequence.add(new XSDouble(XslTransformEvaluationHelper.getStrVal(argVal)));
+                        }
+    
+                        evalResultSequence = (new XSDouble()).constructor(argSequence);
+                        evalResult = evalResultSequence.item(0);
+                        
+                        break;                
+                    case Keywords.XS_INTEGER :
+                        for (int idx = 0; idx < funcExtFunction.getArgCount(); idx++) {
+                            XObject argVal = (funcExtFunction.getArg(idx)).execute(xctxt);
+                            argSequence.add(new XSInteger(XslTransformEvaluationHelper.getStrVal(argVal)));
+                        }
+    
+                        evalResultSequence = (new XSInteger()).constructor(argSequence);
+                        evalResult = evalResultSequence.item(0);
+                        
+                        break;                
+                    case Keywords.XS_LONG :
+                        for (int idx = 0; idx < funcExtFunction.getArgCount(); idx++) {
+                            XObject argVal = (funcExtFunction.getArg(idx)).execute(xctxt);
+                            argSequence.add(new XSLong(XslTransformEvaluationHelper.getStrVal(argVal)));
+                        }
+    
+                        evalResultSequence = (new XSLong()).constructor(argSequence);
+                        evalResult = evalResultSequence.item(0);
+                        
+                        break;
+                    case Keywords.XS_INT :
+                        for (int idx = 0; idx < funcExtFunction.getArgCount(); idx++) {
+                            XObject argVal = (funcExtFunction.getArg(idx)).execute(xctxt);
+                            argSequence.add(new XSInt(XslTransformEvaluationHelper.getStrVal(argVal)));
+                        }
+    
+                        evalResultSequence = (new XSInt()).constructor(argSequence);
+                        evalResult = evalResultSequence.item(0);
+                        
+                        break;
+                    case Keywords.FUNC_BOOLEAN_STRING :
+                        for (int idx = 0; idx < funcExtFunction.getArgCount(); idx++) {
+                            XObject argVal = (funcExtFunction.getArg(idx)).execute(xctxt);
+                            Boolean boolVal = Boolean.valueOf("0".equals(XslTransformEvaluationHelper.getStrVal(argVal)) ? 
+                                                                                     "false" : "true");
+                            argSequence.add(new XSBoolean(boolVal));
+                        }
+    
+                        evalResultSequence = (new XSBoolean()).constructor(argSequence);
+                        evalResult = evalResultSequence.item(0);
+                        
+                        break;
+                    case Keywords.XS_DATE :
+                        for (int idx = 0; idx < funcExtFunction.getArgCount(); idx++) {
+                            XObject argVal = (funcExtFunction.getArg(idx)).execute(xctxt);
+                            argSequence.add(XSDate.parseDate(XslTransformEvaluationHelper.getStrVal(argVal)));
+                        }
+    
+                        evalResultSequence = (new XSDate()).constructor(argSequence); 
+                        evalResult = evalResultSequence.item(0);
+                        
+                        break;
+                    case Keywords.XS_DURATION :
+                        for (int idx = 0; idx < funcExtFunction.getArgCount(); idx++) {
+                            XObject argVal = (funcExtFunction.getArg(idx)).execute(xctxt);
+                            String strVal = XslTransformEvaluationHelper.getStrVal(argVal);
+                            XSDuration xsDuration = XSDuration.parseDuration(strVal);
+                            if (xsDuration != null) {
+                               argSequence.add(xsDuration);
+                               evalResultSequence = (new XSDuration()).constructor(argSequence); 
+                               evalResult = evalResultSequence.item(0);
+                            }
+                            else {
+                               throw new TransformerException("FORG0001 : An incorrectly formatted xs:duration value '" + 
+                                                                                               strVal + "' is present in the input.", srcLocator); 
+                            }
                         }
-                        else {
-                           throw new TransformerException("FORG0001 : an invalid duration value '" + strVal + "' is "
-                                                                                               + "present in the input.", srcLocator); 
+                        
+                        break;
+                    case Keywords.XS_YEAR_MONTH_DURATION :                   
+                        for (int idx = 0; idx < funcExtFunction.getArgCount(); idx++) {
+                            XObject argVal = (funcExtFunction.getArg(idx)).execute(xctxt);
+                            String strVal = XslTransformEvaluationHelper.getStrVal(argVal);
+                            XSDuration xsDuration = XSYearMonthDuration.parseYearMonthDuration(strVal);
+                            if (xsDuration != null) {
+                               argSequence.add(xsDuration);
+                               evalResultSequence = (new XSYearMonthDuration()).constructor(argSequence); 
+                               evalResult = evalResultSequence.item(0);
+                            }
+                            else {
+                                throw new TransformerException("FORG0001 : An incorrectly formatted xs:yearMonthDuration value '" + 
+                                                                                                strVal + "' is present in the input.", srcLocator); 
+                            }
                         }
-                    }                                  
-                }
-                else if ((Keywords.XS_DAY_TIME_DURATION).equals(funcExtFunction.getFunctionName())) {                    
-                    for (int idx = 0; idx < funcExtFunction.getArgCount(); idx++) {
-                        XObject argVal = (funcExtFunction.getArg(idx)).execute(xctxt);
-                        String strVal = XslTransformEvaluationHelper.getStrVal(argVal);
-                        XSDuration xsDuration = XSDayTimeDuration.parseDayTimeDuration(strVal);
-                        if (xsDuration != null) {
-                           ResultSequence argSequence = new ResultSequence();
-                           argSequence.add(xsDuration);
-                           ResultSequence rSeq = (new XSDayTimeDuration()).constructor(argSequence); 
-                           evalResult = rSeq.item(0);
+                        
+                        break;
+                    case Keywords.XS_DAY_TIME_DURATION :                 
+                        for (int idx = 0; idx < funcExtFunction.getArgCount(); idx++) {
+                            XObject argVal = (funcExtFunction.getArg(idx)).execute(xctxt);
+                            String strVal = XslTransformEvaluationHelper.getStrVal(argVal);
+                            XSDuration xsDuration = XSDayTimeDuration.parseDayTimeDuration(strVal);
+                            if (xsDuration != null) {
+                               argSequence.add(xsDuration);
+                               evalResultSequence = (new XSDayTimeDuration()).constructor(argSequence); 
+                               evalResult = evalResultSequence.item(0);
+                            }
+                            else {
+                                throw new TransformerException("FORG0001 : An incorrectly formatted xs:dayTimeDuration value '" + 
+                                                                                                strVal + "' is present in the input.", srcLocator); 
+                            }                            
                         }
-                        else {
-                           throw new TransformerException("FORG0001 : an invalid duration value '" + strVal + "' is "
-                                                                                                + "present in the input.", srcLocator); 
-                        }                            
-                    }
-                }
+                        
+                        break;
+                        
+                    default:
+                       // no op
+                  }
             }
         }
         else if (expr instanceof Operation) {
-            // we need to call this method recursively, for the possibility of more than one
-            // XPath expression evaluation operator present within an XPath expression.
-            // for e.g, a + b - c.
+            // We need to call this method recursively, for the possibility of more than one
+            // XPath expression evaluation operator present within an XPath expression 
+            // (for e.g, a + b - c).
             Operation opn = (Operation)expr;
             XObject leftOperand = processFuncExtFunctionOrXPathOpn(xctxt, opn.getLeftOperand());
             XObject rightOperand = processFuncExtFunctionOrXPathOpn(xctxt, opn.getRightOperand());
diff --git a/src/org/apache/xpath/compiler/Keywords.java b/src/org/apache/xpath/compiler/Keywords.java
index c7541dab..fa281598 100644
--- a/src/org/apache/xpath/compiler/Keywords.java
+++ b/src/org/apache/xpath/compiler/Keywords.java
@@ -379,6 +379,9 @@ public class Keywords
   /** xs:date data type string. */
   public static final String XS_DATE = "date";
   
+  /** xs:duration data type string. */
+  public static final String XS_DURATION = "duration";
+  
   /** xs:yearMonthDuration data type string. */
   public static final String XS_YEAR_MONTH_DURATION = "yearMonthDuration";
   
diff --git a/src/org/apache/xpath/functions/FuncMax.java b/src/org/apache/xpath/functions/FuncMax.java
index 3f8e7642..8533a6dd 100644
--- a/src/org/apache/xpath/functions/FuncMax.java
+++ b/src/org/apache/xpath/functions/FuncMax.java
@@ -33,11 +33,13 @@ import org.apache.xpath.objects.XString;
 import org.apache.xpath.operations.Variable;
 import org.apache.xpath.res.XPATHErrorResources;
 import org.apache.xpath.xs.types.XSDate;
+import org.apache.xpath.xs.types.XSDayTimeDuration;
 import org.apache.xpath.xs.types.XSDouble;
 import org.apache.xpath.xs.types.XSNumericType;
 import org.apache.xpath.xs.types.XSString;
 import org.apache.xpath.xs.types.XSUntyped;
 import org.apache.xpath.xs.types.XSUntypedAtomic;
+import org.apache.xpath.xs.types.XSYearMonthDuration;
 
 /**
  * Implementation of an XPath 3.1 function fn:max.
@@ -87,6 +89,8 @@ public class FuncMax extends FunctionMultiArgs
       int doubleItemCount = 0;
       int strItemCount = 0;
       int dateItemCount = 0;
+      int yearMonthDurationItemCount = 0;
+      int dayTimeDurationItemCount = 0;
       
       if (xObjArg0 instanceof XNodeSet) {
          // If for all the nodes of an input sequence, the node's string
@@ -148,10 +152,15 @@ public class FuncMax extends FunctionMultiArgs
                convetedInpSequence.add((XSDate)seqObj);
                dateItemCount++;
             }
+            else if (seqObj instanceof XSYearMonthDuration) {
+               convetedInpSequence.add((XSYearMonthDuration)seqObj);
+               yearMonthDurationItemCount++;
+            }
+            else if (seqObj instanceof XSDayTimeDuration) {
+               convetedInpSequence.add((XSDayTimeDuration)seqObj);
+               dayTimeDurationItemCount++;
+            }
          }
-         
-         // TO DO : to handle XML Schema types xs:duration (and its subtypes), xs:anyURI as
-         //         well, within function call fn:max's input sequence. 
       }
       else {
          result = xObjArg0;  
@@ -169,16 +178,25 @@ public class FuncMax extends FunctionMultiArgs
          else if ((dateItemCount > 0) && (convetedInpSequence.size() == dateItemCount)) {
             result = getMaxValueFromXSDateSequence(convetedInpSequence);
          }
+         else if ((yearMonthDurationItemCount > 0) && (convetedInpSequence.size() == 
+                                                                              yearMonthDurationItemCount)) {
+            result = getMaxValueFromXSYearMonthDurationSequence(convetedInpSequence);
+         }
+         else if ((dayTimeDurationItemCount > 0) && (convetedInpSequence.size() == 
+                                                                              dayTimeDurationItemCount)) {
+            result = getMaxValueFromXSDayTimeDurationSequence(convetedInpSequence);
+         }
          else if ((xObjArg0 instanceof ResultSequence) && (((ResultSequence)xObjArg0).
                                                                                   size() == 0)) {
             // the result value is an empty sequence
             result = new ResultSequence(); 
          }
          else {
-            throw new javax.xml.transform.TransformerException("FORG0006 : An input sequence processed by function fn:max, "
+            throw new javax.xml.transform.TransformerException("FORG0006 : An input sequence processed by function fn:max "
                                                                      + "should have data values of same type for all the items of "
-                                                                     + "sequence (for e.g, all xs:double, all xs:string, all xs:date "
-                                                                     + "etc).", srcLocator); 
+                                                                     + "sequence (for e.g, all xs:double, all xs:string, all xs:date, "
+                                                                     + "all xs:yearMonthDuration, all xs:dayTimeDuration etc).", 
+                                                                     srcLocator); 
          }
       }
       
@@ -280,6 +298,44 @@ public class FuncMax extends FunctionMultiArgs
      return result;
   }
   
+  /**
+   * Given a sequence of xdm XSYearMonthDuration objects, find the
+   * XSYearMonthDuration object that represents the latest value amongst
+   * the items of the provided sequence.  
+   */
+  private XSYearMonthDuration getMaxValueFromXSYearMonthDurationSequence(
+                                                                     ResultSequence inpSeq) {
+     XSYearMonthDuration result = (XSYearMonthDuration)(inpSeq.item(0));
+         
+     for (int idx = 1; idx < inpSeq.size(); idx++) {
+        XSYearMonthDuration nextVal = (XSYearMonthDuration)(inpSeq.item(idx));
+        if (nextVal.gt(result)) {
+           result = nextVal;   
+        }
+     }
+     
+     return result;
+  }
+  
+  /**
+   * Given a sequence of xdm XSDayTimeDuration objects, find the
+   * XSDayTimeDuration object that represents the latest value amongst
+   * the items of the provided sequence.  
+   */
+  private XSDayTimeDuration getMaxValueFromXSDayTimeDurationSequence(
+                                                                     ResultSequence inpSeq) {
+     XSDayTimeDuration result = (XSDayTimeDuration)(inpSeq.item(0));
+         
+     for (int idx = 1; idx < inpSeq.size(); idx++) {
+        XSDayTimeDuration nextVal = (XSDayTimeDuration)(inpSeq.item(idx));
+        if (nextVal.gt(result)) {
+           result = nextVal;   
+        }
+     }
+     
+     return result;
+  }
+  
   /**
    * Get the string comparison collation uri, for function call fn:max's evaluation.
    */
diff --git a/src/org/apache/xpath/functions/FuncMin.java b/src/org/apache/xpath/functions/FuncMin.java
index 4c80bc6e..97631ac7 100644
--- a/src/org/apache/xpath/functions/FuncMin.java
+++ b/src/org/apache/xpath/functions/FuncMin.java
@@ -33,11 +33,13 @@ import org.apache.xpath.objects.XString;
 import org.apache.xpath.operations.Variable;
 import org.apache.xpath.res.XPATHErrorResources;
 import org.apache.xpath.xs.types.XSDate;
+import org.apache.xpath.xs.types.XSDayTimeDuration;
 import org.apache.xpath.xs.types.XSDouble;
 import org.apache.xpath.xs.types.XSNumericType;
 import org.apache.xpath.xs.types.XSString;
 import org.apache.xpath.xs.types.XSUntyped;
 import org.apache.xpath.xs.types.XSUntypedAtomic;
+import org.apache.xpath.xs.types.XSYearMonthDuration;
 
 /**
  * Implementation of an XPath 3.1 function fn:min.
@@ -87,6 +89,8 @@ public class FuncMin extends FunctionMultiArgs
       int doubleItemCount = 0;
       int strItemCount = 0;
       int dateItemCount = 0;
+      int yearMonthDurationItemCount = 0;
+      int dayTimeDurationItemCount = 0;
       
       if (xObjArg0 instanceof XNodeSet) {
          // If for all the nodes of an input sequence, the node's string
@@ -148,10 +152,15 @@ public class FuncMin extends FunctionMultiArgs
                convetedInpSequence.add((XSDate)seqObj);
                dateItemCount++;
             }
+            else if (seqObj instanceof XSYearMonthDuration) {
+               convetedInpSequence.add((XSYearMonthDuration)seqObj);
+               yearMonthDurationItemCount++;
+            }
+            else if (seqObj instanceof XSDayTimeDuration) {
+               convetedInpSequence.add((XSDayTimeDuration)seqObj);
+               dayTimeDurationItemCount++;
+            }
          }
-         
-         // TO DO : to handle XML Schema types xs:duration (and its subtypes), xs:anyURI as
-         //         well, within function call fn:min's input sequence. 
       }
       else {
          result = xObjArg0;  
@@ -169,16 +178,25 @@ public class FuncMin extends FunctionMultiArgs
          else if ((dateItemCount > 0) && (convetedInpSequence.size() == dateItemCount)) {
             result = getMinValueFromXSDateSequence(convetedInpSequence);
          }
+         else if ((yearMonthDurationItemCount > 0) && (convetedInpSequence.size() == 
+                                                                             yearMonthDurationItemCount)) {
+            result = getMinValueFromXSYearMonthDurationSequence(convetedInpSequence);
+         }
+         else if ((dayTimeDurationItemCount > 0) && (convetedInpSequence.size() == 
+                                                                             dayTimeDurationItemCount)) {
+            result = getMinValueFromXSDayTimeDurationSequence(convetedInpSequence);
+         }
          else if ((xObjArg0 instanceof ResultSequence) && (((ResultSequence)xObjArg0).
                                                                                   size() == 0)) {
             // the result value is an empty sequence
             result = new ResultSequence(); 
          }
          else {
-            throw new javax.xml.transform.TransformerException("FORG0006 : An input sequence processed by function fn:min, "
-                                                                     + "should have data values of same type for all the items of "
-                                                                     + "sequence (for e.g, all xs:double, all xs:string, all xs:date "
-                                                                     + "etc).", srcLocator); 
+            throw new javax.xml.transform.TransformerException("FORG0006 : An input sequence processed by function fn:min "
+                                                                                      + "should have data values of same type for all the items of "
+                                                                                      + "sequence (for e.g, all xs:double, all xs:string, all xs:date, "
+                                                                                      + "all xs:yearMonthDuration, all xs:dayTimeDuration etc).", 
+                                                                                      srcLocator);
          }
       }
       
@@ -280,6 +298,44 @@ public class FuncMin extends FunctionMultiArgs
      return result;
   }
   
+  /**
+   * Given a sequence of xdm XSYearMonthDuration objects, find the
+   * XSYearMonthDuration object that represents the smallest value
+   * amongst the items of the provided sequence.  
+   */
+  private XSYearMonthDuration getMinValueFromXSYearMonthDurationSequence(
+                                                                     ResultSequence inpSeq) {
+     XSYearMonthDuration result = (XSYearMonthDuration)(inpSeq.item(0));
+         
+     for (int idx = 1; idx < inpSeq.size(); idx++) {
+        XSYearMonthDuration nextVal = (XSYearMonthDuration)(inpSeq.item(idx));
+        if (nextVal.lt(result)) {
+           result = nextVal;   
+        }
+     }
+     
+     return result;
+  }
+  
+  /**
+   * Given a sequence of xdm XSDayTimeDuration objects, find the
+   * XSDayTimeDuration object that represents the smallest value
+   * amongst the items of the provided sequence.  
+   */
+  private XSDayTimeDuration getMinValueFromXSDayTimeDurationSequence(
+                                                                     ResultSequence inpSeq) {
+     XSDayTimeDuration result = (XSDayTimeDuration)(inpSeq.item(0));
+         
+     for (int idx = 1; idx < inpSeq.size(); idx++) {
+        XSDayTimeDuration nextVal = (XSDayTimeDuration)(inpSeq.item(idx));
+        if (nextVal.lt(result)) {
+           result = nextVal;   
+        }
+     }
+     
+     return result;
+  }
+  
   /**
    * Get the string comparison collation uri, for function call fn:min's evaluation.
    */
diff --git a/src/org/apache/xpath/xs/types/XSDayTimeDuration.java b/src/org/apache/xpath/xs/types/XSDayTimeDuration.java
index 074768b3..625558ea 100644
--- a/src/org/apache/xpath/xs/types/XSDayTimeDuration.java
+++ b/src/org/apache/xpath/xs/types/XSDayTimeDuration.java
@@ -19,6 +19,10 @@
  */
 package org.apache.xpath.xs.types;
 
+import java.math.BigDecimal;
+
+import javax.xml.transform.TransformerException;
+
 import org.apache.xpath.objects.ResultSequence;
 
 /**
@@ -202,6 +206,110 @@ public class XSDayTimeDuration extends XSDuration {
 		return XS_DAY_TIME_DURATION;
 	}
 	
+	/**
+	 * Method to add an XSDayTimeDuration value, to this 
+	 * XSDayTimeDuration value.
+	 */
+	public XSDayTimeDuration add(XSDayTimeDuration xsDayTimeDuration) {       
+        double sum = value() + xsDayTimeDuration.value();
+
+        return new XSDayTimeDuration(sum);
+    }
+	
+    /**
+     * Method to subtract an XSDayTimeDuration value, from this 
+     * XSDayTimeDuration value.
+     */
+    public XSDayTimeDuration subtract(XSDayTimeDuration xsDayTimeDuration) {       
+        double diff = value() - xsDayTimeDuration.value();
+
+        return new XSDayTimeDuration(diff);
+    }
+    
+    /**
+     * Method to multiply an XSDayTimeDuration value represented by this
+     * object, with a numeric value represented by an argument passed to
+     * this method.
+     * 
+     * @throws TransformerException 
+     */
+    public XSDayTimeDuration mult(XSAnyType xsAnyType) throws TransformerException {
+        
+        XSDayTimeDuration result = null;
+        
+        if (xsAnyType instanceof XSNumericType) {
+           String argStrVal = ((XSNumericType)xsAnyType).stringValue();
+           XSDouble argDoubleVal = new XSDouble(argStrVal);
+           if (argDoubleVal.nan()) {
+              throw new TransformerException("FOCA0005 : Cannot multiply an XSDayTimeDuration value with NaN.");  
+           }
+           else {
+              result = new XSDayTimeDuration(value() * argDoubleVal.doubleValue()); 
+           }
+        }
+        else {
+           throw new TransformerException("FOCA0005 : Cannot multiply an XSDayTimeDuration value with a "
+                                                                                                   + "non-numeric value"); 
+        }
+        
+        return result;
+    }
+    
+    /**
+     * Method to divide this XSDayTimeDuration value, by a value (that needs to be
+     * either a numeric value or a XSDayTimeDuration value) that is passed as an
+     * argument to this method.
+     * 
+     * @throws TransformerException 
+     */
+    public XSDayTimeDuration div(XSAnyType xsAnyType) throws TransformerException {
+        
+        XSDayTimeDuration result = null;
+        
+        if (xsAnyType instanceof XSNumericType) {
+           String argStrVal = ((XSNumericType)xsAnyType).stringValue();
+           XSDouble argDoubleVal = new XSDouble(argStrVal);
+           if (argDoubleVal.nan()) {
+              throw new TransformerException("FOCA0005 : Cannot divide an XSDayTimeDuration value with NaN.");  
+           }
+           else if (argDoubleVal.zero()) {
+              throw new TransformerException("FODT0001 : Cannot divide an XSDayTimeDuration value with zero."); 
+           }
+           else if (argDoubleVal.infinite()) {
+              double doubleResultVal = value() / argDoubleVal.doubleValue();
+              result = new XSDayTimeDuration(doubleResultVal);
+           }
+           else {
+              BigDecimal bigDecimal1 = new BigDecimal(value());
+              BigDecimal bigDecimal2 = new BigDecimal(argDoubleVal.doubleValue());
+              BigDecimal bigDecimalResult = bigDecimal1.divide(new BigDecimal(bigDecimal2.doubleValue()), 
+                                                                                                 18, BigDecimal.ROUND_HALF_EVEN);
+              result = new XSDayTimeDuration(bigDecimalResult.doubleValue());
+           }
+        }
+        else if (xsAnyType instanceof XSDayTimeDuration) {
+           double dbl2 = ((XSDayTimeDuration)xsAnyType).seconds();
+           
+           if (dbl2 != 0) {
+               BigDecimal bigDecimal1 = new BigDecimal(value());
+               BigDecimal bigDecimal2 = new BigDecimal(dbl2);
+               BigDecimal bigDecimalResult = bigDecimal1.divide(new BigDecimal(bigDecimal2.doubleValue()), 
+                                                                                                  18, BigDecimal.ROUND_HALF_EVEN);
+               result = new XSDayTimeDuration(bigDecimalResult.doubleValue());  
+           }
+           else {
+              throw new TransformerException("FODT0001 : Cannot divide an XSDayTimeDuration value, with a XSDayTimeDuration "
+                                                                                               + "value that represents zero seconds."); 
+           }
+        }
+        else {
+           throw new TransformerException("FORG0006 : Cannot divide an XSDayTimeDuration value, with a value that is of "
+                                                                                   + "a type other than numeric or XSDayTimeDuration.");
+        }
+        
+        return result;
+    }
+	
 	/**
      * Do a data type cast, of a XSAnyType value to an XSDuration
      * value. 
diff --git a/src/org/apache/xpath/xs/types/XSDuration.java b/src/org/apache/xpath/xs/types/XSDuration.java
index 72be5b33..81656f5f 100644
--- a/src/org/apache/xpath/xs/types/XSDuration.java
+++ b/src/org/apache/xpath/xs/types/XSDuration.java
@@ -20,6 +20,8 @@
  */
 package org.apache.xpath.xs.types;
 
+import javax.xml.transform.TransformerException;
+
 import org.apache.xpath.objects.ResultSequence;
 
 /**
@@ -31,7 +33,9 @@ import org.apache.xpath.objects.ResultSequence;
  */
 public class XSDuration extends XSCtrType {
 
-	private static final String XS_DURATION = "xs:duration";
+    private static final long serialVersionUID = -8460416911698841833L;
+
+    private static final String XS_DURATION = "xs:duration";
 	
 	protected int _year;
 	protected int _month;
@@ -248,41 +252,56 @@ public class XSDuration extends XSCtrType {
 		ret += seconds();
 
 		if (negative()) {
-			ret *= -1;
+		   ret *= -1;
 		}
 		
 		return ret;
 	}
 	
-	public double time_value() {
+	public double timeValue() {
 		double ret = 0;
 		ret += hours() * 60 * 60;
 		ret += minutes() * 60;
 		ret += seconds();
 
-		if (negative())
-			ret *= -1;
+		if (negative()) {
+		   ret *= -1;
+		}
+		
 		return ret;
 	}
 
 	/**
-	 * TO DO
-	 */
-	public ResultSequence constructor(ResultSequence arg) {
-		ResultSequence rs = null;		
-
-		return rs;
+     * A method to construct an xdm sequence comprising a
+     * xs:duration value, given input data as argument to 
+     * this method.
+     * 
+	 * @throws TransformerException 
+     */
+	public ResultSequence constructor(ResultSequence arg) throws TransformerException {
+	    ResultSequence resultSeq = new ResultSequence();
+	    
+	    if (arg.size() == 0) {
+	       return resultSeq;     
+	    }
+	    
+	    XSAnyType xsAnyType = (XSAnyType)arg.item(0);
+	    
+        XSDuration xsDuration = castToDuration(xsAnyType);
+        
+        resultSeq.add(xsDuration);
+
+		return resultSeq;
 	}
 
 	/**
-	 * Construct a new XSDuration object, by parsing the 
-	 * supplied string.
+	 * Construct a new XSDuration object, by parsing the supplied string.
 	 * 
 	 * @param str   string to be parsed
 	 * 
 	 * @return      XSDuration object representing the duration of time supplied
 	 */
-	public static XSDuration parse(String str) {
+	public static XSDuration parseDuration(String str) throws TransformerException {
 		boolean negative = false;
 		int years = 0;
 		int months = 0;
@@ -291,29 +310,28 @@ public class XSDuration extends XSCtrType {
 		int minutes = 0;
 		double seconds = 0;
 
-		// string following the P
 		String pstr = "";
 		String tstr = "";
 
-		// get the negative and pstr
 		if (str.startsWith("-P")) {
 			negative = true;
 			pstr = str.substring(2, str.length());
 		} else if (str.startsWith("P")) {
 			negative = false;
 			pstr = str.substring(1, str.length());
-		} else
+		} else {
 			return null;
+		}
 
 		try {
 			int index = pstr.indexOf('Y');
-			boolean did_something = false;
+			boolean isAction = false;
 
 			if (index != -1) {
 				String digit = pstr.substring(0, index);
 				years = Integer.parseInt(digit);
 				pstr = pstr.substring(index + 1, pstr.length());
-				did_something = true;
+				isAction = true;
 			}
 
 			index = pstr.indexOf('M');
@@ -321,10 +339,10 @@ public class XSDuration extends XSCtrType {
 				String digit = pstr.substring(0, index);
 				months = Integer.parseInt(digit);
 				pstr = pstr.substring(index + 1, pstr.length());
-				did_something = true;
+				isAction = true;
 			}
 
-			// get the days
+			// days
 			index = pstr.indexOf('D');
 
 			if (index == -1) {
@@ -340,25 +358,25 @@ public class XSDuration extends XSCtrType {
 					tstr = tstr.substring(1, tstr.length());
 				} else {
 					tstr = "";
-					did_something = true;
+					isAction = true;
 				}
 			}
 
-			// hour
+			// hours
 			index = tstr.indexOf('H');
 			if (index != -1) {
 				String digit = tstr.substring(0, index);
 				hours = Integer.parseInt(digit);
 				tstr = tstr.substring(index + 1, tstr.length());
-				did_something = true;
+				isAction = true;
 			}
-			// minute
+			// minutes
 			index = tstr.indexOf('M');
 			if (index != -1) {
 				String digit = tstr.substring(0, index);
 				minutes = Integer.parseInt(digit);
 				tstr = tstr.substring(index + 1, tstr.length());
-				did_something = true;
+				isAction = true;
 			}
 			// seconds
 			index = tstr.indexOf('S');
@@ -366,14 +384,15 @@ public class XSDuration extends XSCtrType {
 				String digit = tstr.substring(0, index);
 				seconds = Double.parseDouble(digit);
 				tstr = tstr.substring(index + 1, tstr.length());
-				did_something = true;
+				isAction = true;
 			}
-			if (!did_something) {
+			if (!isAction) {
 				return null;
 			}
 
 		} catch (NumberFormatException ex) {
-			return null;
+			throw new TransformerException("FORG0001 : The provided string, cannot be parsed "
+			                                                                   + "to a xs:duration value."); 
 		}
 
 		return new XSDuration(years, months, days, hours, minutes, seconds, negative);
@@ -396,5 +415,56 @@ public class XSDuration extends XSCtrType {
 	public int month() {
 		return _month;
 	}
+	
+	/**
+	 * This method does an equality comparison between, this and
+	 * another XSDuration value. 
+	 */
+	public boolean equals(XSDuration xsDuration) {
+       double val1 = value();
+       double val2 = xsDuration.value();
+       
+       return val1 == val2;
+    }
+	
+	/**
+     * This method checks whether, this XSDuration value is less
+     * than another one.  
+     */
+    public boolean lt(XSDuration xsDuration) {
+       double val1 = value();
+       double val2 = xsDuration.value();
+       
+       return val1 < val2;
+    }
+    
+    /**
+     * This method checks whether, this XSDuration value is
+     * greater than another one.  
+     */
+    public boolean gt(XSDuration xsDuration) {
+       double val1 = value();
+       double val2 = xsDuration.value();
+       
+       return val1 > val2;
+    }
+    
+    /**
+     * Do a data type cast, of a XSAnyType value to an XSDuration
+     * value.
+     *  
+     * @throws TransformerException 
+     */
+    private XSDuration castToDuration(XSAnyType xsAnyType) throws TransformerException {
+        
+        if (xsAnyType instanceof XSDuration) {
+            XSDuration duration = (XSDuration) xsAnyType;
+            
+            return new XSDuration(duration.year(), duration.month(), duration.days(), duration.hours(), 
+                                                              duration.minutes(), duration.seconds(), duration.negative());
+        }
+        
+        return parseDuration(xsAnyType.stringValue());
+    }
 
 }
diff --git a/src/org/apache/xpath/xs/types/XSYearMonthDuration.java b/src/org/apache/xpath/xs/types/XSYearMonthDuration.java
index fcd721cb..f143b34e 100644
--- a/src/org/apache/xpath/xs/types/XSYearMonthDuration.java
+++ b/src/org/apache/xpath/xs/types/XSYearMonthDuration.java
@@ -19,7 +19,10 @@
  */
 package org.apache.xpath.xs.types;
 
-import org.apache.xpath.XPathException;
+import java.math.BigDecimal;
+
+import javax.xml.transform.TransformerException;
+
 import org.apache.xpath.objects.ResultSequence;
 
 /**
@@ -245,12 +248,46 @@ public class XSYearMonthDuration extends XSDuration {
     public int monthValue() {
        int retVal = (year() * 12) + month();
 
-       if (negative())
+       if (negative()) {
           retVal *= -1;
+       }
 
        return retVal;
     }
     
+    /**
+     * This method does an equality comparison between, this and
+     * another XSYearMonthDuration value. 
+     */
+    public boolean equals(XSYearMonthDuration xsYearMonthDuration) {
+       double val1 = monthValue();
+       double val2 = xsYearMonthDuration.monthValue();
+       
+       return val1 == val2;
+    }
+    
+    /**
+     * This method checks whether, this XSYearMonthDuration value is
+     * less than another one.  
+     */
+    public boolean lt(XSYearMonthDuration xsYearMonthDuration) {
+       double val1 = monthValue();
+       double val2 = xsYearMonthDuration.monthValue();
+       
+       return val1 < val2;
+    }
+    
+    /**
+     * This method checks whether, this XSYearMonthDuration value is
+     * greater than another one.  
+     */
+    public boolean gt(XSYearMonthDuration xsYearMonthDuration) {
+       double val1 = monthValue();
+       double val2 = xsYearMonthDuration.monthValue();
+       
+       return val1 > val2;
+    }
+    
     /**
      * Add two XSYearMonthDuration values, and return the result
      * as an XSYearMonthDuration value.
@@ -272,56 +309,73 @@ public class XSYearMonthDuration extends XSDuration {
     }
     
     /**
-     * Multiply an XSYearMonthDuration value by a numeric value, and return the 
-     * result as an XSYearMonthDuration value.
+     * Method to multiply an XSYearMonthDuration value represented by this
+     * object, with a numeric value represented by an argument passed to
+     * this method.
+     * 
+     * @throws TransformerException 
      */
-    public XSYearMonthDuration mult(XSDouble arg) throws XPathException {
-       XSYearMonthDuration result = null;
-       
-       if (arg.nan()) {
-          throw new XPathException("FOCA0005 : NaN supplied as float/double value.");    
-       }
-       
-       if (arg.infinite()) {
-          throw new XPathException("FODT0001 : Overflow/underflow of value for the "
-                                                                         + "date/time operation.");
-       }
-       
-       int intVal = (int)Math.round(monthValue() * arg.doubleValue());
-       
-       result = new XSYearMonthDuration(intVal);
-       
-       return result; 
+    public XSYearMonthDuration mult(XSAnyType xsAnyType) throws TransformerException {
+        
+        XSYearMonthDuration result = null;
+        
+        if (xsAnyType instanceof XSNumericType) {
+           String argStrVal = ((XSNumericType)xsAnyType).stringValue();
+           XSDouble argDoubleVal = new XSDouble(argStrVal);
+           if (argDoubleVal.nan()) {
+              throw new TransformerException("FOCA0005 : Cannot multiply an XSYearMonthDuration value with NaN.");  
+           }
+           else {
+              int res = (int) Math.round(monthValue() * argDoubleVal.doubleValue());
+               
+              result = new XSYearMonthDuration(res); 
+           }
+        }
+        else {
+           throw new TransformerException("FOCA0005 : Cannot multiply an XSYearMonthDuration value with a "
+                                                                                                   + "non-numeric value"); 
+        }
+        
+        return result;
     }
     
     /**
-     * Divide an XSYearMonthDuration value by a numeric value, and return the 
-     * result as an XSYearMonthDuration value.
+     * Method to divide this XSYearMonthDuration value, by a value (that needs to be
+     * either a numeric value or a XSYearMonthDuration value) that is passed as an
+     * argument to this method.
+     * 
+     * @throws TransformerException 
      */
-    public XSYearMonthDuration div(XSDouble arg) throws XPathException {
-        XSYearMonthDuration result = null;
+    public XSAnyType div(XSAnyType xsAnyType) throws TransformerException {
         
-        if (arg.nan()) {
-           throw new XPathException("FOCA0005 : NaN supplied as float/double value.");    
-        }
+        XSAnyType result = null;
         
-        if (arg.infinite()) {
-           result = new XSYearMonthDuration(0); 
-        }
-        else {
-           XSDouble xsDouble = (XSDouble)arg;
-
-           if (!arg.zero()) {
-              int intVal = (int)Math.round(monthValue() / xsDouble.doubleValue());
-              result = new XSYearMonthDuration(intVal); 
+        if (xsAnyType instanceof XSNumericType) {
+           String argStrVal = ((XSNumericType)xsAnyType).stringValue();
+           XSDouble argDoubleVal = new XSDouble(argStrVal);
+           if (argDoubleVal.nan()) {
+              throw new TransformerException("FOCA0005 : Cannot divide an XSYearMonthDuration value with NaN.");  
+           }
+           else if (argDoubleVal.zero()) {
+              throw new TransformerException("FODT0001 : Cannot divide an XSYearMonthDuration value with zero."); 
            }
            else {
-              throw new XPathException("FODT0001 : Overflow/underflow of value for the "
-                                                                                    + "date/time operation."); 
-           } 
+              int intResultVal = (int) Math.round(monthValue() / argDoubleVal.doubleValue());
+              result = new XSYearMonthDuration(intResultVal);
+           }
         }
-
-        return result;
+        else if (xsAnyType instanceof XSYearMonthDuration) {
+           XSYearMonthDuration argXSYearMonthDuration = (XSYearMonthDuration) xsAnyType;
+           double dblResultVal = (double) monthValue() / argXSYearMonthDuration.monthValue();
+           
+           result = new XSDecimal(new BigDecimal(dblResultVal));
+        }
+        else {
+           throw new TransformerException("FORG0006 : Cannot divide an XSYearMonthDuration value, with a value that is of "
+                                                                                   + "a type other than numeric or XSYearMonthDuration.");
+        }
+        
+        return result; 
     }
     
     /**
diff --git a/tests/fn_max/gold/test3.out b/tests/fn_max/gold/test3.out
new file mode 100644
index 00000000..37769264
--- /dev/null
+++ b/tests/fn_max/gold/test3.out
@@ -0,0 +1 @@
+<?xml version="1.0" encoding="UTF-8"?><result>c</result>
diff --git a/tests/fn_max/gold/test4.out b/tests/fn_max/gold/test4.out
new file mode 100644
index 00000000..c83abe5d
--- /dev/null
+++ b/tests/fn_max/gold/test4.out
@@ -0,0 +1 @@
+<?xml version="1.0" encoding="UTF-8"?><result>P2Y2M</result>
diff --git a/tests/fn_max/gold/test5.out b/tests/fn_max/gold/test5.out
new file mode 100644
index 00000000..7a70f149
--- /dev/null
+++ b/tests/fn_max/gold/test5.out
@@ -0,0 +1 @@
+<?xml version="1.0" encoding="UTF-8"?><result>P6DT11H32M20S</result>
diff --git a/tests/fn_max/test1_b.xml b/tests/fn_max/test1_b.xml
new file mode 100644
index 00000000..c958b047
--- /dev/null
+++ b/tests/fn_max/test1_b.xml
@@ -0,0 +1,5 @@
+<info>
+  <val>a</val>
+  <val>c</val>
+  <val>b</val>
+</info>
\ No newline at end of file
diff --git a/tests/fn_max/test3.xsl b/tests/fn_max/test3.xsl
new file mode 100644
index 00000000..187aa249
--- /dev/null
+++ b/tests/fn_max/test3.xsl
@@ -0,0 +1,47 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
+                xmlns:xs="http://www.w3.org/2001/XMLSchema"
+                exclude-result-prefixes="xs"
+                version="3.0">
+                
+    <!-- Author: mukulg@apache.org -->
+   
+    <!-- use with test1_b.xml -->
+   
+    <!-- An XSLT stylesheet test, to test the XPath 3.1 fn:max() 
+         function. Within this stylesheet, while finding the
+         maximum value amongst XML sibling element nodes, we
+         wish to treat each XML element as having a type
+         annotation xs:string.
+         
+         This stylesheet, gets an input data to be transformed
+         from an XML external document.
+    -->                
+    
+    <xsl:output method="xml" indent="yes"/>
+    
+    <xsl:template match="/info">
+       <result>
+         <xsl:value-of select="max(for $val in * return xs:string($val))"/>
+       </result> 
+    </xsl:template>
+    
+    <!--
+      * Licensed to the Apache Software Foundation (ASF) under one
+      * or more contributor license agreements. See the NOTICE file
+      * distributed with this work for additional information
+      * regarding copyright ownership. The ASF licenses this file
+      * to you under the Apache License, Version 2.0 (the  "License");
+      * you may not use this file except in compliance with the License.
+      * You may obtain a copy of the License at
+      *
+      *     http://www.apache.org/licenses/LICENSE-2.0
+      *
+      * Unless required by applicable law or agreed to in writing, software
+      * distributed under the License is distributed on an "AS IS" BASIS,
+      * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+      * See the License for the specific language governing permissions and
+      * limitations under the License.
+    -->
+    
+</xsl:stylesheet>
\ No newline at end of file
diff --git a/tests/fn_max/test4.xsl b/tests/fn_max/test4.xsl
new file mode 100644
index 00000000..66cfb79e
--- /dev/null
+++ b/tests/fn_max/test4.xsl
@@ -0,0 +1,43 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
+                xmlns:xs="http://www.w3.org/2001/XMLSchema"
+                exclude-result-prefixes="xs"
+                version="3.0">
+                
+    <!-- Author: mukulg@apache.org -->
+   
+    <!-- An XSLT stylesheet test, to test the XPath 3.1 function 
+         fn:max. Within this stylesheet, we find the maximum
+         value within a sequence of xs:yearMonthDuration values.
+    -->                 
+    
+    <xsl:output method="xml" indent="yes"/>
+        
+    <xsl:variable name="seq1" select="(xs:yearMonthDuration('P1Y3M'), xs:yearMonthDuration('P2Y2M'), 
+                                                     xs:yearMonthDuration('P3M'), xs:yearMonthDuration('P1Y5M'))"/>
+        
+    <xsl:template match="/">
+       <result>
+          <xsl:value-of select="max($seq1)"/>
+       </result> 
+    </xsl:template>
+    
+    <!--
+      * Licensed to the Apache Software Foundation (ASF) under one
+      * or more contributor license agreements. See the NOTICE file
+      * distributed with this work for additional information
+      * regarding copyright ownership. The ASF licenses this file
+      * to you under the Apache License, Version 2.0 (the  "License");
+      * you may not use this file except in compliance with the License.
+      * You may obtain a copy of the License at
+      *
+      *     http://www.apache.org/licenses/LICENSE-2.0
+      *
+      * Unless required by applicable law or agreed to in writing, software
+      * distributed under the License is distributed on an "AS IS" BASIS,
+      * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+      * See the License for the specific language governing permissions and
+      * limitations under the License.
+    -->
+    
+</xsl:stylesheet>
\ No newline at end of file
diff --git a/tests/fn_max/test5.xsl b/tests/fn_max/test5.xsl
new file mode 100644
index 00000000..b3373bc1
--- /dev/null
+++ b/tests/fn_max/test5.xsl
@@ -0,0 +1,43 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
+                xmlns:xs="http://www.w3.org/2001/XMLSchema"
+                exclude-result-prefixes="xs"
+                version="3.0">
+                
+    <!-- Author: mukulg@apache.org -->
+   
+    <!-- An XSLT stylesheet test, to test the XPath 3.1 function 
+         fn:max. Within this stylesheet, we find the maximum
+         value within a sequence of xs:dayTimeDuration values.
+    -->                 
+    
+    <xsl:output method="xml" indent="yes"/>
+        
+    <xsl:variable name="seq1" select="(xs:dayTimeDuration('PT40H'), xs:dayTimeDuration('P6DT11H32M20S'), 
+                                                                                                 xs:dayTimeDuration('P2DT3H'))"/>
+        
+    <xsl:template match="/">
+       <result>
+          <xsl:value-of select="max($seq1)"/>
+       </result> 
+    </xsl:template>
+    
+    <!--
+      * Licensed to the Apache Software Foundation (ASF) under one
+      * or more contributor license agreements. See the NOTICE file
+      * distributed with this work for additional information
+      * regarding copyright ownership. The ASF licenses this file
+      * to you under the Apache License, Version 2.0 (the  "License");
+      * you may not use this file except in compliance with the License.
+      * You may obtain a copy of the License at
+      *
+      *     http://www.apache.org/licenses/LICENSE-2.0
+      *
+      * Unless required by applicable law or agreed to in writing, software
+      * distributed under the License is distributed on an "AS IS" BASIS,
+      * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+      * See the License for the specific language governing permissions and
+      * limitations under the License.
+    -->
+    
+</xsl:stylesheet>
\ No newline at end of file
diff --git a/tests/fn_min/gold/test3.out b/tests/fn_min/gold/test3.out
new file mode 100644
index 00000000..21a2c20e
--- /dev/null
+++ b/tests/fn_min/gold/test3.out
@@ -0,0 +1 @@
+<?xml version="1.0" encoding="UTF-8"?><result>P3M</result>
diff --git a/tests/fn_min/gold/test4.out b/tests/fn_min/gold/test4.out
new file mode 100644
index 00000000..e2017da4
--- /dev/null
+++ b/tests/fn_min/gold/test4.out
@@ -0,0 +1 @@
+<?xml version="1.0" encoding="UTF-8"?><result>P1DT16H</result>
diff --git a/tests/fn_min/test3.xsl b/tests/fn_min/test3.xsl
new file mode 100644
index 00000000..0a2c1ee1
--- /dev/null
+++ b/tests/fn_min/test3.xsl
@@ -0,0 +1,43 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
+                xmlns:xs="http://www.w3.org/2001/XMLSchema"
+                exclude-result-prefixes="xs"
+                version="3.0">
+                
+    <!-- Author: mukulg@apache.org -->
+   
+    <!-- An XSLT stylesheet test, to test the XPath 3.1 function 
+         fn:min. Within this stylesheet, we find the minimum
+         value within a sequence of xs:yearMonthDuration values.
+    -->                 
+    
+    <xsl:output method="xml" indent="yes"/>
+        
+    <xsl:variable name="seq1" select="(xs:yearMonthDuration('P1Y3M'), xs:yearMonthDuration('P2Y2M'), 
+                                                     xs:yearMonthDuration('P3M'), xs:yearMonthDuration('P1Y5M'))"/>
+        
+    <xsl:template match="/">
+       <result>
+          <xsl:value-of select="min($seq1)"/>
+       </result> 
+    </xsl:template>
+    
+    <!--
+      * Licensed to the Apache Software Foundation (ASF) under one
+      * or more contributor license agreements. See the NOTICE file
+      * distributed with this work for additional information
+      * regarding copyright ownership. The ASF licenses this file
+      * to you under the Apache License, Version 2.0 (the  "License");
+      * you may not use this file except in compliance with the License.
+      * You may obtain a copy of the License at
+      *
+      *     http://www.apache.org/licenses/LICENSE-2.0
+      *
+      * Unless required by applicable law or agreed to in writing, software
+      * distributed under the License is distributed on an "AS IS" BASIS,
+      * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+      * See the License for the specific language governing permissions and
+      * limitations under the License.
+    -->
+    
+</xsl:stylesheet>
\ No newline at end of file
diff --git a/tests/fn_min/test4.xsl b/tests/fn_min/test4.xsl
new file mode 100644
index 00000000..7771c586
--- /dev/null
+++ b/tests/fn_min/test4.xsl
@@ -0,0 +1,43 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
+                xmlns:xs="http://www.w3.org/2001/XMLSchema"
+                exclude-result-prefixes="xs"
+                version="3.0">
+                
+    <!-- Author: mukulg@apache.org -->
+   
+    <!-- An XSLT stylesheet test, to test the XPath 3.1 function 
+         fn:min. Within this stylesheet, we find the minimum
+         value within a sequence of xs:dayTimeDuration values.
+    -->                 
+    
+    <xsl:output method="xml" indent="yes"/>
+        
+    <xsl:variable name="seq1" select="(xs:dayTimeDuration('PT40H'), xs:dayTimeDuration('P6DT11H32M20S'), 
+                                                                                                 xs:dayTimeDuration('P2DT3H'))"/>
+        
+    <xsl:template match="/">
+       <result>
+          <xsl:value-of select="min($seq1)"/>
+       </result> 
+    </xsl:template>
+    
+    <!--
+      * Licensed to the Apache Software Foundation (ASF) under one
+      * or more contributor license agreements. See the NOTICE file
+      * distributed with this work for additional information
+      * regarding copyright ownership. The ASF licenses this file
+      * to you under the Apache License, Version 2.0 (the  "License");
+      * you may not use this file except in compliance with the License.
+      * You may obtain a copy of the License at
+      *
+      *     http://www.apache.org/licenses/LICENSE-2.0
+      *
+      * Unless required by applicable law or agreed to in writing, software
+      * distributed under the License is distributed on an "AS IS" BASIS,
+      * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+      * See the License for the specific language governing permissions and
+      * limitations under the License.
+    -->
+    
+</xsl:stylesheet>
\ No newline at end of file
diff --git a/tests/fn_sort/gold/test16.out b/tests/fn_sort/gold/test16.out
new file mode 100644
index 00000000..14b27963
--- /dev/null
+++ b/tests/fn_sort/gold/test16.out
@@ -0,0 +1,32 @@
+<?xml version="1.0" encoding="UTF-8"?><result>
+  <data1>
+    <d>are</d>
+    <h>for testing</h>
+    <a>hi</a>
+    <c>how</c>
+    <b>there</b>
+    <f>this is an</f>
+    <g>xml document</g>
+    <e>you</e>
+  </data1>
+  <data2>
+    <d>are</d>
+    <h>for testing</h>
+    <a>hi</a>
+    <c>how</c>
+    <b>there</b>
+    <f>this is an</f>
+    <g>xml document</g>
+    <e>you</e>
+  </data2>
+  <data3>
+    <d>are</d>
+    <h>for testing</h>
+    <a>hi</a>
+    <c>how</c>
+    <b>there</b>
+    <f>this is an</f>
+    <g>xml document</g>
+    <e>you</e>
+  </data3>
+</result>
diff --git a/tests/fn_sort/test19.xsl b/tests/fn_sort/test19.xsl
new file mode 100644
index 00000000..bfaf4a3e
--- /dev/null
+++ b/tests/fn_sort/test19.xsl
@@ -0,0 +1,57 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
+                xmlns:xs="http://www.w3.org/2001/XMLSchema"
+                exclude-result-prefixes="xs"
+                version="3.0">
+                
+    <!-- Author: mukulg@apache.org -->
+   
+    <!-- use with test1_i.xml -->
+   
+    <!-- An XSLT stylesheet test case, to test an XPath 3.1
+         function fn:sort, using collations.
+    -->
+    
+    <xsl:output method="xml" indent="yes"/>
+    
+    <xsl:variable name="collation1" select="'http://www.w3.org/2005/xpath-functions/collation/codepoint'"/>
+    
+    <xsl:variable name="collation2" select="'http://www.w3.org/2013/collation/UCA?lang=en'"/>
+    
+    <xsl:template match="/info">
+       <result>
+         <data1>
+           <!-- implicitly using 'Unicode codepoint collation' -->
+           <xsl:copy-of select="sort(*, (), function($elem) { xs:string($elem) })"/>
+         </data1>
+         <data2>
+           <!-- explicitly requesting 'Unicode codepoint collation', via a collation uri -->
+	       <xsl:copy-of select="sort(*, $collation1, function($elem) { xs:string($elem) })"/>
+         </data2>
+         <data3>
+           <!-- requesting to use 'Unicode Collation Algorithm', via a collation uri 
+                with collation language as English (using language code, 'en'). -->
+	       <xsl:copy-of select="sort(*, $collation2, function($elem) { xs:string($elem) })"/>
+         </data3>
+       </result> 
+    </xsl:template>
+    
+    <!--
+      * Licensed to the Apache Software Foundation (ASF) under one
+      * or more contributor license agreements. See the NOTICE file
+      * distributed with this work for additional information
+      * regarding copyright ownership. The ASF licenses this file
+      * to you under the Apache License, Version 2.0 (the  "License");
+      * you may not use this file except in compliance with the License.
+      * You may obtain a copy of the License at
+      *
+      *     http://www.apache.org/licenses/LICENSE-2.0
+      *
+      * Unless required by applicable law or agreed to in writing, software
+      * distributed under the License is distributed on an "AS IS" BASIS,
+      * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+      * See the License for the specific language governing permissions and
+      * limitations under the License.
+    -->
+    
+</xsl:stylesheet>
\ No newline at end of file
diff --git a/tests/fn_sort/test1_i.xml b/tests/fn_sort/test1_i.xml
new file mode 100644
index 00000000..ee2a0f3a
--- /dev/null
+++ b/tests/fn_sort/test1_i.xml
@@ -0,0 +1,10 @@
+<info>
+  <a>hi</a>
+  <b>there</b>
+  <c>how</c>
+  <d>are</d>
+  <e>you</e>
+  <f>this is an</f>
+  <g>xml document</g>
+  <h>for testing</h>
+</info>
\ No newline at end of file
diff --git a/tests/org/apache/xalan/xpath3/FnMaxTests.java b/tests/org/apache/xalan/xpath3/FnMaxTests.java
index 6f6f7720..30e9ff42 100644
--- a/tests/org/apache/xalan/xpath3/FnMaxTests.java
+++ b/tests/org/apache/xalan/xpath3/FnMaxTests.java
@@ -68,5 +68,35 @@ public class FnMaxTests extends XslTransformTestsUtil {
         
         runXslTransformAndAssertOutput(xmlFilePath, xslFilePath, goldFilePath, null);
     }
+    
+    @Test
+    public void xslFnMaxTest3() {
+        String xmlFilePath = XSL_TRANSFORM_INPUT_DIRPATH + "test1_b.xml"; 
+        String xslFilePath = XSL_TRANSFORM_INPUT_DIRPATH + "test3.xsl";
+        
+        String goldFilePath = XSL_TRANSFORM_GOLD_DIRPATH + "test3.out";                
+        
+        runXslTransformAndAssertOutput(xmlFilePath, xslFilePath, goldFilePath, null);
+    }
+    
+    @Test
+    public void xslFnMaxTest4() {
+        String xmlFilePath = XSL_TRANSFORM_INPUT_DIRPATH + "test4.xsl"; 
+        String xslFilePath = XSL_TRANSFORM_INPUT_DIRPATH + "test4.xsl";
+        
+        String goldFilePath = XSL_TRANSFORM_GOLD_DIRPATH + "test4.out";                
+        
+        runXslTransformAndAssertOutput(xmlFilePath, xslFilePath, goldFilePath, null);
+    }
+    
+    @Test
+    public void xslFnMaxTest5() {
+        String xmlFilePath = XSL_TRANSFORM_INPUT_DIRPATH + "test5.xsl"; 
+        String xslFilePath = XSL_TRANSFORM_INPUT_DIRPATH + "test5.xsl";
+        
+        String goldFilePath = XSL_TRANSFORM_GOLD_DIRPATH + "test5.out";                
+        
+        runXslTransformAndAssertOutput(xmlFilePath, xslFilePath, goldFilePath, null);
+    }
 
 }
diff --git a/tests/org/apache/xalan/xpath3/FnMinTests.java b/tests/org/apache/xalan/xpath3/FnMinTests.java
index 56881cb6..0f59d657 100644
--- a/tests/org/apache/xalan/xpath3/FnMinTests.java
+++ b/tests/org/apache/xalan/xpath3/FnMinTests.java
@@ -68,5 +68,25 @@ public class FnMinTests extends XslTransformTestsUtil {
         
         runXslTransformAndAssertOutput(xmlFilePath, xslFilePath, goldFilePath, null);
     }
+    
+    @Test
+    public void xslFnMinTest3() {
+        String xmlFilePath = XSL_TRANSFORM_INPUT_DIRPATH + "test3.xsl"; 
+        String xslFilePath = XSL_TRANSFORM_INPUT_DIRPATH + "test3.xsl";
+        
+        String goldFilePath = XSL_TRANSFORM_GOLD_DIRPATH + "test3.out";                
+        
+        runXslTransformAndAssertOutput(xmlFilePath, xslFilePath, goldFilePath, null);
+    }
+    
+    @Test
+    public void xslFnMinTest4() {
+        String xmlFilePath = XSL_TRANSFORM_INPUT_DIRPATH + "test4.xsl"; 
+        String xslFilePath = XSL_TRANSFORM_INPUT_DIRPATH + "test4.xsl";
+        
+        String goldFilePath = XSL_TRANSFORM_GOLD_DIRPATH + "test4.out";                
+        
+        runXslTransformAndAssertOutput(xmlFilePath, xslFilePath, goldFilePath, null);
+    }
 
 }
diff --git a/tests/org/apache/xalan/xpath3/FnSortTests.java b/tests/org/apache/xalan/xpath3/FnSortTests.java
index d8373c92..b4ea1874 100644
--- a/tests/org/apache/xalan/xpath3/FnSortTests.java
+++ b/tests/org/apache/xalan/xpath3/FnSortTests.java
@@ -228,5 +228,15 @@ public class FnSortTests extends XslTransformTestsUtil {
         
         runXslTransformAndAssertOutput(xmlFilePath, xslFilePath, goldFilePath, null);
     }
+    
+    @Test
+    public void xslFnSortTest19() {
+        String xmlFilePath = XSL_TRANSFORM_INPUT_DIRPATH + "test1_i.xml"; 
+        String xslFilePath = XSL_TRANSFORM_INPUT_DIRPATH + "test19.xsl";
+        
+        String goldFilePath = XSL_TRANSFORM_GOLD_DIRPATH + "test16.out";                
+        
+        runXslTransformAndAssertOutput(xmlFilePath, xslFilePath, goldFilePath, null);
+    }
 
 }


---------------------------------------------------------------------
To unsubscribe, e-mail: commits-unsubscribe@xalan.apache.org
For additional commands, e-mail: commits-help@xalan.apache.org