generate float instead of double if constraints suggest this
diff --git a/libasn1compiler/asn1c_misc.c b/libasn1compiler/asn1c_misc.c
index 59cb497..086a8fa 100644
--- a/libasn1compiler/asn1c_misc.c
+++ b/libasn1compiler/asn1c_misc.c
@@ -215,7 +215,7 @@
 			}
 		}
 
-		if(_format == TNF_CTYPE) {
+		if(_format == TNF_CTYPE || _format == TNF_CONSTYPE) {
 			/*
 			 * If the component references the type itself,
 			 * switch to a recursion-safe type naming
@@ -236,18 +236,36 @@
 	case ASN_BASIC_ENUMERATED:
 	case ASN_BASIC_REAL:
 		if((expr->expr_type == ASN_BASIC_REAL
-			&& !(arg->flags & A1C_USE_WIDE_TYPES))
+			&& (_format == TNF_CONSTYPE || !(arg->flags & A1C_USE_WIDE_TYPES)))
 		|| asn1c_type_fits_long(arg, expr)) {
 			switch(_format) {
-			case TNF_CTYPE:
-			case TNF_RSAFE:
-				if(expr->expr_type == ASN_BASIC_REAL)
-					return "double";
-				else if(asn1c_type_fits_long(arg, expr) == FL_FITS_UNSIGN)
-					return "unsigned long";
-				else
-					return "long";
-			default:
+			case TNF_CONSTYPE:
+				if(expr->expr_type == ASN_BASIC_REAL) {
+                    return "double";
+                } else if(asn1c_type_fits_long(arg, expr) == FL_FITS_UNSIGN) {
+                    return "unsigned long";
+                } else {
+                    return "long";
+                }
+            case TNF_CTYPE:
+            case TNF_RSAFE:
+                if(expr->expr_type == ASN_BASIC_REAL) {
+                    asn1cnst_range_t *range = asn1constraint_compute_OER_range(
+                        expr->Identifier, ASN_BASIC_REAL,
+                        expr->combined_constraints, ACT_EL_RANGE, 0, 0, 0);
+                    if(range->narrowing == NARROW_FLOAT32) {
+                        asn1constraint_range_free(range);
+                        return "float";
+                    } else {
+                        asn1constraint_range_free(range);
+                        return "double";
+                    }
+                } else if(asn1c_type_fits_long(arg, expr) == FL_FITS_UNSIGN) {
+                    return "unsigned long";
+                } else {
+                    return "long";
+                }
+            default:
 				typename = 0;
 				switch(expr->expr_type) {
 				case ASN_BASIC_INTEGER:
@@ -298,6 +316,7 @@
 	case TNF_SAFE:
 		return asn1c_make_identifier(0, exprid, typename, (char*)0);
 	case TNF_CTYPE:	/* C type */
+	case TNF_CONSTYPE:	/* C type */
 		return asn1c_make_identifier(0, exprid,
 				exprid?"t":typename, exprid?0:"t", (char*)0);
 	case TNF_RSAFE:	/* Recursion-safe type */