Makefile fixup
[org.ibex.tool.git] / repo / org.ibex.tool / src / org / eclipse / jdt / internal / compiler / problem / DefaultProblemFactory.java
1 /*******************************************************************************
2  * Copyright (c) 2000, 2004 IBM Corporation and others.
3  * All rights reserved. This program and the accompanying materials 
4  * are made available under the terms of the Common Public License v1.0
5  * which accompanies this distribution, and is available at
6  * http://www.eclipse.org/legal/cpl-v10.html
7  * 
8  * Contributors:
9  *     IBM Corporation - initial API and implementation
10  *******************************************************************************/
11 package org.eclipse.jdt.internal.compiler.problem;
12
13 import java.util.Enumeration;
14 import java.util.Locale;
15 import java.util.MissingResourceException;
16 import java.util.ResourceBundle;
17
18 import org.eclipse.jdt.core.compiler.*;
19 import org.eclipse.jdt.core.compiler.IProblem;
20 import org.eclipse.jdt.internal.compiler.IProblemFactory;
21 import org.eclipse.jdt.internal.compiler.util.HashtableOfInt;
22 import org.eclipse.jdt.internal.compiler.util.Util;
23
24 public class DefaultProblemFactory implements IProblemFactory {
25
26         public HashtableOfInt messageTemplates;
27         private Locale locale;
28         private static HashtableOfInt DEFAULT_LOCALE_TEMPLATES;
29         private final static char[] DOUBLE_QUOTES = "''".toCharArray(); //$NON-NLS-1$
30         private final static char[] SINGLE_QUOTE = "'".toCharArray(); //$NON-NLS-1$
31
32 public DefaultProblemFactory() {
33         this(Locale.getDefault());
34 }
35 /**
36  * @param loc the locale used to get the right message
37  */
38 public DefaultProblemFactory(Locale loc) {
39         this.locale = loc;
40         if (Locale.getDefault().equals(loc)){
41                 if (DEFAULT_LOCALE_TEMPLATES == null){
42                         DEFAULT_LOCALE_TEMPLATES = loadMessageTemplates(loc);
43                 }
44                 this.messageTemplates = DEFAULT_LOCALE_TEMPLATES;
45         } else {
46                 this.messageTemplates = loadMessageTemplates(loc);
47         }
48 }
49 /**
50  * Answer a new IProblem created according to the parameters value
51  * <ul>
52  * <li>originatingFileName the name of the file name from which the problem is originated
53  * <li>problemId the problem id
54  * <li>problemArguments the fully qualified arguments recorded inside the problem
55  * <li>messageArguments the arguments needed to set the error message (shorter names than problemArguments ones)
56  * <li>severity the severity of the problem
57  * <li>startPosition the starting position of the problem
58  * <li>endPosition the end position of the problem
59  * <li>lineNumber the line on which the problem occured
60  * </ul>
61  * @param originatingFileName char[]
62  * @param problemId int
63  * @param problemArguments String[]
64  * @param messageArguments String[]
65  * @param severity int
66  * @param startPosition int
67  * @param endPosition int
68  * @param lineNumber int
69  * @return org.eclipse.jdt.internal.compiler.IProblem
70  */
71 public IProblem createProblem(
72         char[] originatingFileName, 
73         int problemId, 
74         String[] problemArguments, 
75         String[] messageArguments, 
76         int severity, 
77         int startPosition, 
78         int endPosition, 
79         int lineNumber) {
80
81         return new DefaultProblem(
82                 originatingFileName, 
83                 this.getLocalizedMessage(problemId, messageArguments),
84                 problemId, 
85                 problemArguments, 
86                 severity, 
87                 startPosition, 
88                 endPosition, 
89                 lineNumber); 
90 }
91 private final static int keyFromID(int id) {
92     return id + 1; // keys are offsetted by one in table, since it cannot handle 0 key
93 }
94 /**
95  * Answer the locale used to retrieve the error messages
96  * @return java.util.Locale
97  */
98 public Locale getLocale() {
99         return this.locale;
100 }
101 public final String getLocalizedMessage(int id, String[] problemArguments) {
102         String message = (String) this.messageTemplates.get(keyFromID(id & IProblem.IgnoreCategoriesMask)); 
103         if (message == null) {
104                 return "Unable to retrieve the error message for problem id: " //$NON-NLS-1$
105                         + (id & IProblem.IgnoreCategoriesMask)
106                         + ". Check compiler resources.";  //$NON-NLS-1$
107         }
108
109         // for compatibility with MessageFormat which eliminates double quotes in original message
110         char[] messageWithNoDoubleQuotes =
111                 CharOperation.replace(message.toCharArray(), DOUBLE_QUOTES, SINGLE_QUOTE);
112
113         if (problemArguments == null) return new String(messageWithNoDoubleQuotes);
114
115         int length = messageWithNoDoubleQuotes.length;
116         int start = 0;
117         int end = length;
118         StringBuffer output = null;
119         if ((id & IProblem.Javadoc) != 0) {
120                 if (output == null) output = new StringBuffer(10+length+problemArguments.length*20);
121                 output.append((String) this.messageTemplates.get(keyFromID(IProblem.JavadocMessagePrefix & IProblem.IgnoreCategoriesMask)));
122         }
123         while (true) {
124                 if ((end = CharOperation.indexOf('{', messageWithNoDoubleQuotes, start)) > -1) {
125                         if (output == null) output = new StringBuffer(length+problemArguments.length*20);
126                         output.append(messageWithNoDoubleQuotes, start, end - start);
127                         if ((start = CharOperation.indexOf('}', messageWithNoDoubleQuotes, end + 1)) > -1) {
128                                 int index = -1;
129                                 String argId = new String(messageWithNoDoubleQuotes, end + 1, start - end - 1);
130                                 try {
131                                         index = Integer.parseInt(argId);
132                                         output.append(problemArguments[index]);
133                                 } catch (NumberFormatException nfe) {
134                                         output.append(messageWithNoDoubleQuotes, end + 1, start - end);
135                                 } catch (ArrayIndexOutOfBoundsException e) {
136                                         return "Cannot bind message for problem (id: " //$NON-NLS-1$
137                                                 + (id & IProblem.IgnoreCategoriesMask)
138                                                 + ") \""  //$NON-NLS-1$
139                                                 + message
140                                                 + "\" with arguments: {" //$NON-NLS-1$
141                                                 + Util.toString(problemArguments)
142                                                 +"}"; //$NON-NLS-1$
143                                 }
144                                 start++;
145                         } else {
146                                 output.append(messageWithNoDoubleQuotes, end, length);
147                                 break;
148                         }
149                 } else {
150                         if (output == null) return new String(messageWithNoDoubleQuotes);
151                         output.append(messageWithNoDoubleQuotes, start, length - start);
152                         break;
153                 }
154         }
155
156         return output.toString();
157 }
158 /**
159  * @param problem org.eclipse.jdt.internal.compiler.IProblem
160  * @return String
161  */
162 public final String localizedMessage(IProblem problem) {
163         return getLocalizedMessage(problem.getID(), problem.getArguments());
164 }
165
166 /**
167  * This method initializes the MessageTemplates class variable according
168  * to the current Locale.
169  * @param loc Locale
170  * @return HashtableOfInt
171  */
172 public static HashtableOfInt loadMessageTemplates(Locale loc) {
173         ResourceBundle bundle = null;
174         String bundleName = "org.eclipse.jdt.internal.compiler.problem.messages"; //$NON-NLS-1$
175         try {
176                 bundle = ResourceBundle.getBundle(bundleName, loc); 
177         } catch(MissingResourceException e) {
178                 System.out.println("Missing resource : " + bundleName.replace('.', '/') + ".properties for locale " + loc); //$NON-NLS-1$//$NON-NLS-2$
179                 throw e;
180         }
181         HashtableOfInt templates = new HashtableOfInt(700);
182         Enumeration keys = bundle.getKeys();
183         while (keys.hasMoreElements()) {
184             String key = (String)keys.nextElement();
185             try {
186                 int messageID = Integer.parseInt(key);
187                         templates.put(keyFromID(messageID), bundle.getString(key));
188             } catch(NumberFormatException e) {
189                 // key ill-formed
190                 } catch (MissingResourceException e) {
191                         // available ID
192             }
193         }
194         return templates;
195 }
196
197 }