1
/*
2
 * gchardet.cpp
3
 * Copyright (C) 2009 Adrian Perez <aperez@igalia.com>
4
 */
5
6
#include "gchardet.h"
7
#include "nscore.h"
8
#include "nsUniversalDetector.h"
9
#include <string.h>
10
11
12
class CharsetDetector : public nsUniversalDetector
13
{
14
public:
15
  CharsetDetector (PRUint32 aLanguageFilter)
16
    : nsUniversalDetector (aLanguageFilter) {}
17
  bool GetDone () const { return mDone; }
18
  const char* GetCharset () const { return mDetectedCharset; }
19
protected:
20
  virtual void Report(const char* aCharset);
21
};
22
23
24
void CharsetDetector::Report(const char* aCharset)
25
{
26
  (void) aCharset; /* Keep compiler happy */
27
}
28
29
30
31
g_chardet_t*
32
g_chardet_new (guint32 lang_filter)
33
{
34
  return reinterpret_cast <void*> (new CharsetDetector (lang_filter));
35
}
36
37
38
gboolean
39
g_chardet_handle (g_chardet_t *cd,
40
                  const gchar *buf,
41
                  guint32      len)
42
{
43
  nsresult rv;
44
  g_return_val_if_fail (cd != NULL, 0);
45
46
  CharsetDetector *impl = reinterpret_cast <CharsetDetector*> (cd);
47
48
  /*
49
   * If the charset was already found, there is no need to keep supplying
50
   * data: report that properly to our caller.
51
   */
52
  if (impl -> GetDone ())
53
    return false;
54
55
  rv = impl -> HandleData (buf, len);
56
57
  /*
58
   * In theory, the only error so far we can get out of the character set
59
   * detector is NS_ERROR_OUT_OF_MEMORY. This is done only for some sanity
60
   * checking, because OOM conditions are are likely to continue happening,
61
   * so if we force the caller to continue supplygin data and there is free
62
   * memory in later invocations, things should work.
63
   */
64
  if (rv != NS_OK)
65
    g_return_val_if_fail (rv == NS_ERROR_OUT_OF_MEMORY, true);
66
67
  return ! impl -> GetDone ();
68
}
69
70
71
void
72
g_chardet_free (g_chardet_t *cd)
73
{
74
  g_return_if_fail (cd != NULL);
75
  CharsetDetector *impl = reinterpret_cast <CharsetDetector*> (cd);
76
  delete impl;
77
}
78
79
const gchar*
80
g_chardet_charset (g_chardet_t *cd)
81
{
82
  g_return_val_if_fail (cd != NULL, NULL);
83
  CharsetDetector *impl = reinterpret_cast <CharsetDetector*> (cd);
84
  return (impl -> GetDone()) ? impl -> GetCharset() : NULL;
85
}
86
87
88
gboolean
89
g_chardet_found (g_chardet_t *cd)
90
{
91
  g_return_val_if_fail (cd != NULL, FALSE);
92
  CharsetDetector *impl = reinterpret_cast <CharsetDetector*> (cd);
93
  return impl -> GetDone();
94
}
95
96
void
97
g_chardet_finish (g_chardet_t *cd)
98
{
99
  g_return_if_fail (cd != NULL);
100
  CharsetDetector *impl = reinterpret_cast <CharsetDetector*> (cd);
101
  impl -> DataEnd ();
102
}
103
104
105
gchar*
106
g_chardet_detect  (const gchar *string, guint32 lang_filter)
107
{
108
  g_return_val_if_fail (string != NULL, NULL);
109
  CharsetDetector impl (lang_filter);
110
  impl.HandleData (string, strlen (string));
111
  return g_strdup (impl.GetCharset ());
112
}