Merge mozilla-central to autoland

This commit is contained in:
Carsten "Tomcat" Book 2016-11-29 11:50:17 +01:00
commit 9dd582c3dd
236 changed files with 7083 additions and 5227 deletions

View File

@ -22,4 +22,4 @@
# changes to stick? As of bug 928195, this shouldn't be necessary! Please
# don't change CLOBBER for WebIDL changes any more.
Merge day clobber
Bug 1309272, part 5 renames gfx/thebes/PrintTargetCG.cpp (to .mm) which results in an object file of the same name, requiring a clobber.

View File

@ -17,7 +17,7 @@ const TEST_THRESHOLD = {
};
const ADDON_ROLLOUT_POLICY = {
"beta" : "51alladdons", // Any WebExtension or addon with mpc = true
"beta" : "51alladdons", // Any WebExtension or addon except with mpc = false
"release" : "50allmpc", // Any WebExtension or addon with mpc = true
};

View File

@ -406,6 +406,8 @@
@RESPATH@/components/NetworkGeolocationProvider.manifest
@RESPATH@/components/NetworkGeolocationProvider.js
@RESPATH@/components/extensions.manifest
@RESPATH@/components/EditorUtils.manifest
@RESPATH@/components/EditorUtils.js
@RESPATH@/components/addonManager.js
@RESPATH@/components/amContentHandler.js
@RESPATH@/components/amInstallTrigger.js

View File

@ -1,5 +1,4 @@
#include <functional>
#include "mozilla/Function.h"
#define MOZ_STRONG_REF __attribute__((annotate("moz_strong_ref")))
struct RefCountedBase {
@ -220,107 +219,6 @@ void b() {
});
}
void c() {
R* ptr;
SmartPtr<R> sp;
mozilla::function<void(R*)>([&](R* argptr) {
R* localptr;
ptr->method();
argptr->method();
localptr->method();
});
mozilla::function<void(SmartPtr<R>)>([&](SmartPtr<R> argsp) {
SmartPtr<R> localsp;
sp->method();
argsp->method();
localsp->method();
});
mozilla::function<void(R*)>([&](R* argptr) {
R* localptr;
take(ptr);
take(argptr);
take(localptr);
});
mozilla::function<void(SmartPtr<R>)>([&](SmartPtr<R> argsp) {
SmartPtr<R> localsp;
take(sp);
take(argsp);
take(localsp);
});
mozilla::function<void(R*)>([=](R* argptr) {
R* localptr;
ptr->method(); // expected-error{{Refcounted variable 'ptr' of type 'R' cannot be captured by a lambda}} expected-note{{Please consider using a smart pointer}}
argptr->method();
localptr->method();
});
mozilla::function<void(SmartPtr<R>)>([=](SmartPtr<R> argsp) {
SmartPtr<R> localsp;
sp->method();
argsp->method();
localsp->method();
});
mozilla::function<void(R*)>([=](R* argptr) {
R* localptr;
take(ptr); // expected-error{{Refcounted variable 'ptr' of type 'R' cannot be captured by a lambda}} expected-note{{Please consider using a smart pointer}}
take(argptr);
take(localptr);
});
mozilla::function<void(SmartPtr<R>)>([=](SmartPtr<R> argsp) {
SmartPtr<R> localsp;
take(sp);
take(argsp);
take(localsp);
});
mozilla::function<void(R*)>([ptr](R* argptr) { // expected-error{{Refcounted variable 'ptr' of type 'R' cannot be captured by a lambda}} expected-note{{Please consider using a smart pointer}}
R* localptr;
ptr->method();
argptr->method();
localptr->method();
});
mozilla::function<void(SmartPtr<R>)>([sp](SmartPtr<R> argsp) {
SmartPtr<R> localsp;
sp->method();
argsp->method();
localsp->method();
});
mozilla::function<void(R*)>([ptr](R* argptr) { // expected-error{{Refcounted variable 'ptr' of type 'R' cannot be captured by a lambda}} expected-note{{Please consider using a smart pointer}}
R* localptr;
take(ptr);
take(argptr);
take(localptr);
});
mozilla::function<void(SmartPtr<R>)>([sp](SmartPtr<R> argsp) {
SmartPtr<R> localsp;
take(sp);
take(argsp);
take(localsp);
});
mozilla::function<void(R*)>([&ptr](R* argptr) {
R* localptr;
ptr->method();
argptr->method();
localptr->method();
});
mozilla::function<void(SmartPtr<R>)>([&sp](SmartPtr<R> argsp) {
SmartPtr<R> localsp;
sp->method();
argsp->method();
localsp->method();
});
mozilla::function<void(R*)>([&ptr](R* argptr) {
R* localptr;
take(ptr);
take(argptr);
take(localptr);
});
mozilla::function<void(SmartPtr<R>)>([&sp](SmartPtr<R> argsp) {
SmartPtr<R> localsp;
take(sp);
take(argsp);
take(localsp);
});
}
// These tests would check c++14 deduced return types, if they were supported in
// our codebase. They are being kept here for convenience in the future if we do
// add support for c++14 deduced return types

View File

@ -71,14 +71,21 @@ def rust_compiler(value, rustc, rustc_info):
set_config('MOZ_RUST', rust_compiler)
@depends(rust_compiler, rustc, target)
@imports('os')
@imports('subprocess')
@imports(_from='mozbuild.configure.util', _import='LineIO')
@imports(_from='mozbuild.shellutil', _import='quote')
@imports(_from='tempfile', _import='mkstemp')
def rust_target(rust_compiler, rustc, target):
if rust_compiler:
@template
def rust_triple_alias(host_or_target):
"""Template defining the alias used for rustc's --target flag.
`host_or_target` is either `host` or `target` (the @depends functions
from init.configure).
"""
assert host_or_target in (host, target)
@depends(rustc, host_or_target, when=rust_compiler)
@imports('os')
@imports('subprocess')
@imports(_from='mozbuild.configure.util', _import='LineIO')
@imports(_from='mozbuild.shellutil', _import='quote')
@imports(_from='tempfile', _import='mkstemp')
def rust_target(rustc, host_or_target):
# Rust's --target options are similar to, but not exactly the same
# as, the autoconf-derived targets we use. An example would be that
# Rust uses distinct target triples for targetting the GNU C++ ABI
@ -93,7 +100,7 @@ def rust_target(rust_compiler, rustc, target):
# Avoid having to write out os+kernel for all the platforms where
# they don't differ.
os_or_kernel = target.kernel if target.kernel == 'Linux' and target.os != 'Android' else target.os
os_or_kernel = host_or_target.kernel if host_or_target.kernel == 'Linux' and host_or_target.os != 'Android' else host_or_target.os
rustc_target = {
# DragonFly
('x86_64', 'DragonFly'): 'x86_64-unknown-dragonfly',
@ -120,10 +127,10 @@ def rust_target(rust_compiler, rustc, target):
# we need i686-pc-windows-gnu instead, since mingw32 builds work.
('x86', 'WINNT'): 'i686-pc-windows-msvc',
('x86_64', 'WINNT'): 'x86_64-pc-windows-msvc',
}.get((target.cpu, os_or_kernel), None)
}.get((host_or_target.cpu, os_or_kernel), None)
if rustc_target is None:
die("Don't know how to translate {} for rustc".format(target.alias))
die("Don't know how to translate {} for rustc".format(host_or_target.alias))
# Check to see whether our rustc has a reasonably functional stdlib
# for our chosen target.
@ -148,19 +155,26 @@ def rust_target(rust_compiler, rustc, target):
in_path,
]
def failed():
die('Cannot compile for {} with {}'.format(target.alias, rustc))
die('Cannot compile for {} with {}'.format(host_or_target.alias, rustc))
check_cmd_output(*cmd, onerror=failed)
if not os.path.exists(out_path) or os.path.getsize(out_path) == 0:
failed()
finally:
os.remove(in_path)
os.remove(out_path)
# This target is usable.
return rustc_target
set_config('RUST_TARGET', rust_target)
return rust_target
rust_target_triple = rust_triple_alias(target)
rust_host_triple = rust_triple_alias(host)
set_config('RUST_TARGET', rust_target_triple)
set_config('RUST_HOST_TARGET', rust_host_triple)
# Until we remove all the other Rust checks in old-configure.
add_old_configure_assignment('MOZ_RUST', rust_compiler)
add_old_configure_assignment('RUSTC', rustc)
add_old_configure_assignment('RUST_TARGET', rust_target)
add_old_configure_assignment('RUST_TARGET', rust_target_triple)

View File

@ -208,3 +208,314 @@
fun:_ZN6SkOptsL4initEv
fun:sk_once_no_arg_adaptor
}
###################################################
# For valgrind-mochitest ("tc-M-V [tier 2]") runs on taskcluster.
# See bug 1248365.
# These are specific to Ubuntu 12.04.5, 64-bit.
###################################################
# Not sure what this is. Is it the well-known
# Memcheck-being-confused-by-zlib thing? I suspect so.
#
# Conditional jump or move depends on uninitialised value(s)
# at 0xB6154E0: inflateReset2 (in /lib/x86_64-linux-gnu/libz.so.1.2.3.4)
# by 0xB6155D8: inflateInit2_ (in /lib/x86_64-linux-gnu/libz.so.1.2.3.4)
# by 0xADDE253: png_create_read_struct_2
# (in /lib/x86_64-linux-gnu/libpng12.so.0.46.0)
# Uninitialised value was created by a heap allocation
# at 0x4C2D027: malloc (coregrind/m_replacemalloc/vg_replace_malloc.c:298)
# by 0xADE960F: png_malloc (in /lib/x86_64-linux-gnu/libpng12.so.0.46.0)
# by 0xADD1B95: ??? (in /lib/x86_64-linux-gnu/libpng12.so.0.46.0)
# by 0xB6155B6: inflateInit2_ (in /lib/x86_64-linux-gnu/libz.so.1.2.3.4)
# by 0xADDE253: png_create_read_struct_2
# (in /lib/x86_64-linux-gnu/libpng12.so.0.46.0)
# by 0x15707869: ??? (in /usr/lib/x86_64-linux-gnu/gdk-pixbuf-2.0/2.10.0/
# loaders/libpixbufloader-png.so)
{
Bug 1248365: mochitest-libz-1
Memcheck:Cond
fun:inflateReset2
fun:inflateInit2_
fun:png_create_read_struct_2
}
# I don't know what this is.
#
# Conditional jump or move depends on uninitialised value(s)
# at 0x39608257: ??? (in /usr/lib/x86_64-linux-gnu/librsvg-2.so.2.36.1)
# by 0x39608E96: rsvg_handle_get_pixbuf_sub (in /usr/lib/x86_64-linux-gnu/l
# by 0x37D00D2A: ??? (in /usr/lib/x86_64-linux-gnu/gdk-pixbuf-2.0/2.10.0/lo
# by 0x88FF740: gdk_pixbuf_loader_close (in /usr/lib/x86_64-linux-gnu/libgd
# by 0x88FBA48: ??? (in /usr/lib/x86_64-linux-gnu/libgdk_pixbuf-2.0.so.0.26
# by 0x88FD290: gdk_pixbuf_new_from_stream_at_scale (in /usr/lib/x86_64-lin
# by 0x6EF96A7: ??? (in /usr/lib/x86_64-linux-gnu/libgtk-3.so.0.400.2)
# by 0x6EFC2B1: gtk_icon_info_load_icon (in /usr/lib/x86_64-linux-gnu/libgt
# Uninitialised value was created by a stack allocation
# at 0xAB786B0: ??? (in /usr/lib/x86_64-linux-gnu/libpixman-1.so.0.30.2)
{
Bug 1248365: mochitest-librsvg-1
Memcheck:Cond
obj:/*/librsvg-2.so.2.36*
fun:rsvg_handle_get_pixbuf_sub
obj:/*/libpixbufloader-svg.so*
fun:gdk_pixbuf_loader_close
}
# There now follow some suppressions to do with libpixman. There are two
# variants, one for errors in the system libpixman, and one for errors in
# our in-tree copy. I suspect that all of these sse2 compositing reports
# are Memcheck false positives, possibly to do with inaccurate
# instrumentation of the function combine1() in
# gfx/cairo/libpixman/src/pixman-sse2.c.
#
# Conditional jump or move depends on uninitialised value(s)
# at 0xAB93A10: ??? (in /usr/lib/x86_64-linux-gnu/libpixman-1.so.0.30.2)
# by 0xAB78927: ??? (in /usr/lib/x86_64-linux-gnu/libpixman-1.so.0.30.2)
# by 0xAB40B0B: pixman_image_composite32 (in /usr/lib/x86_64-linux-gnu/libp
# by 0x865C95C: ??? (in /usr/lib/x86_64-linux-gnu/libcairo.so.2.11000.2)
# by 0x865E3CB: ??? (in /usr/lib/x86_64-linux-gnu/libcairo.so.2.11000.2)
# by 0x865F6EA: ??? (in /usr/lib/x86_64-linux-gnu/libcairo.so.2.11000.2)
# by 0x865F968: ??? (in /usr/lib/x86_64-linux-gnu/libcairo.so.2.11000.2)
# by 0x867D7C3: ??? (in /usr/lib/x86_64-linux-gnu/libcairo.so.2.11000.2)
# Uninitialised value was created by a stack allocation
# at 0xAB786B0: ??? (in /usr/lib/x86_64-linux-gnu/libpixman-1.so.0.30.2)
{
Bug 1248365: mochitest-libpixman-1
Memcheck:Cond
obj:/*/libpixman-1.so.0.30*
obj:/*/libpixman-1.so.0.30*
fun:pixman_image_composite32
}
# Conditional jump or move depends on uninitialised value(s)
# at 0xF9EA219: sse2_composite_over_8888_8888
# by 0xF9F5B5F: _moz_pixman_image_composite32
# by 0xF96E29E: _clip_and_composite_boxes
# by 0xF96F79D: _cairo_image_surface_fill
# by 0xF98790C: _cairo_surface_fill
# by 0xF96FE2E: _cairo_gstate_fill
# by 0xF98B3D9: _moz_cairo_fill_preserve
# by 0xE4CF383: mozilla::gfx::DrawTargetCairo::DrawPattern(mozilla::gfx:
# Uninitialised value was created by a stack allocation
# at 0xB8E46B0: ??? (in /usr/lib/x86_64-linux-gnu/libpixman-1.so.0.30.2)
{
Bug 1248365: mochitest-libpixman-2
Memcheck:Cond
fun:sse2_composite_over_8888_8888
fun:_moz_pixman_image_composite32
fun:_clip_and_composite_boxes
fun:_cairo_image_surface_fill
}
# Conditional jump or move depends on uninitialised value(s)
# at 0xF9D56AE: sse2_combine_over_u (in /home/worker/workspace/build/applic
# by 0xF9D05D4: general_composite_rect (in /home/worker/workspace/build/app
# by 0xF9F5B5F: _moz_pixman_image_composite32 (in /home/worker/workspace/bu
# by 0xF96CF63: _clip_and_composite (in /home/worker/workspace/build/applic
# by 0xF96D656: _clip_and_composite_boxes.part.32 (in /home/worker/workspac
# by 0xF96E328: _clip_and_composite_boxes (in /home/worker/workspace/build/
# by 0xF96F79D: _cairo_image_surface_fill (in /home/worker/workspace/build/
# by 0xF98790C: _cairo_surface_fill (in /home/worker/workspace/build/applic
# Uninitialised value was created by a stack allocation
# at 0xF9D024D: general_composite_rect (in /home/worker/workspace/build/app
#
{
Bug 1248365: mochitest-libpixman-3
Memcheck:Cond
fun:sse2_combine_over_u
fun:general_composite_rect
fun:_moz_pixman_image_composite32
fun:_clip_and_composite*
}
# Conditional jump or move depends on uninitialised value(s)
# at 0xE626A5C: mozilla::image::imgFrame::Optimize() (in /home/worker/work
# by 0xE626C68: mozilla::image::imgFrame::UnlockImageData() (in /home/work
# by 0xE608E8F: mozilla::image::RawAccessFrameRef::~RawAccessFrameRef() (i
# by 0xE61F5E4: mozilla::image::Decoder::~Decoder() (in /home/worker/works
# by 0xE630E32: mozilla::image::nsIconDecoder::~nsIconDecoder() (in /home/
# by 0xE61A5B2: mozilla::image::Decoder::Release() (in /home/worker/worksp
# by 0xE61DD73: mozilla::image::NotifyDecodeCompleteWorker::~NotifyDecodeC
# by 0xE61DD8F: mozilla::image::NotifyDecodeCompleteWorker::~NotifyDecodeC
# Uninitialised value was created by a stack allocation
# at 0xB8E46B0: ??? (in /usr/lib/x86_64-linux-gnu/libpixman-1.so.0.30.2)
{
Bug 1248365: mochitest-libpixman-4
Memcheck:Cond
fun:_ZN7mozilla5image8imgFrame8OptimizeEv
fun:_ZN7mozilla5image8imgFrame15UnlockImageDataEv
fun:_ZN7mozilla5image17RawAccessFrameRefD1Ev
fun:_ZN7mozilla5image7DecoderD1Ev
}
# Not sure what this. I can't reproduce it locally despite much trying.
# Syscall param sendmsg(msg.msg_iov[0]) points to uninitialised byte(s)
# at 0x4E4533D: ??? (syscall-template.S:82)
# by 0xE12C0A7: IPC::Channel::ChannelImpl::ProcessOutgoingMessages() (in /h
# by 0xE142FD0: RunnableMethod<IPC::Channel, bool (IPC::Channel::*)(IPC::Me
# by 0xE1240EA: MessageLoop::RunTask(Task*) (in /home/worker/workspace/buil
# by 0xE128A46: MessageLoop::DeferOrRunPendingTask(MessageLoop::PendingTask
# by 0xE128B6D: MessageLoop::DoWork() (in /home/worker/workspace/build/appl
# by 0xE12272C: base::MessagePumpLibevent::Run(base::MessagePump::Delegate*
# by 0xE124155: MessageLoop::Run() (in /home/worker/workspace/build/applica
{
Bug 1248365: mochitest-sendmsg-1
Memcheck:Param
sendmsg(msg.msg_iov[0])
obj:/lib/x86_64-linux-gnu/libpthread-2.15.so
fun:_ZN3IPC7Channel11ChannelImpl23ProcessOutgoingMessagesEv
fun:_ZN14RunnableMethodIN3IPC7ChannelEMS1_FbPNS0_7MessageEEN7mozilla5Tuple*
}
# I can't repro this either.
# Conditional jump or move depends on uninitialised value(s)
# at 0x418E7E7C: ??? (in /usr/lib/x86_64-linux-gnu/libavcodec.so.53.35.0)
# by 0x4192D620: ??? (in /usr/lib/x86_64-linux-gnu/libavcodec.so.53.35.0)
# by 0x4192E717: ??? (in /usr/lib/x86_64-linux-gnu/libavcodec.so.53.35.0)
# by 0x41711BC4: ??? (in /usr/lib/x86_64-linux-gnu/libavcodec.so.53.35.0)
# by 0x41B08B6A: avcodec_open2 (in /usr/lib/x86_64-linux-gnu/libavcodec.so.
# by 0xEEAD89C: mozilla::FFmpegDataDecoder<53>::InitDecoder() (in /home/wor
# by 0xEEAE42B: mozilla::FFmpegVideoDecoder<53>::Init() (in /home/worker/wo
# by 0xEEA4C07: mozilla::H264Converter::Init() (in /home/worker/workspace/b
# Uninitialised value was created by a heap allocation
# at 0x4C2D11F: realloc (vg_replace_malloc.c:785)
# by 0x406196: moz_xrealloc (in /home/worker/workspace/build/application/fi
# by 0xDEB43AC: nsTArrayInfallibleAllocator::ResultTypeProxy nsTArray_base<
# by 0xEEAD850: mozilla::FFmpegDataDecoder<53>::InitDecoder() (in /home/wor
# by 0xEEAE42B: mozilla::FFmpegVideoDecoder<53>::Init() (in /home/worker/wo
{
Bug 1248365: mochitest-libavcodec-1-c
Memcheck:Cond
obj:/*/libavcodec.so.53*
obj:/*/libavcodec.so.53*
obj:/*/libavcodec.so.53*
obj:/*/libavcodec.so.53*
}
{
Bug 1248365: mochitest-libavcodec-1-v8
Memcheck:Value8
obj:/*/libavcodec.so.53*
obj:/*/libavcodec.so.53*
obj:/*/libavcodec.so.53*
obj:/*/libavcodec.so.53*
}
# Not sure what this is, but I am inclined to think it is also probably a
# SSE2-induced false positive similar to mochitest-libpixman-2 above.
# Use of uninitialised value of size 8
# at 0xE4F3E89: FastConvertYUVToRGB32Row (in /home/worker/workspace/build/a
# by 0xE4F4A6D: mozilla::gfx::ConvertYCbCrToRGB32(unsigned char const*, uns
# by 0xE4F4B17: mozilla::gfx::ConvertYCbCrToRGB(mozilla::layers::PlanarYCbC
# by 0xE5227CB: mozilla::layers::PlanarYCbCrImage::GetAsSourceSurface() (in
# by 0xE5B2465: mozilla::layers::SharedPlanarYCbCrImage::GetAsSourceSurface
# by 0xE52FE44: mozilla::layers::BasicImageLayer::Paint(mozilla::gfx::DrawT
# by 0xE5618A1: mozilla::layers::BasicLayerManager::PaintSelfOrChildren(moz
# by 0xE560F83: mozilla::layers::BasicLayerManager::PaintLayer(gfxContext*,
# Uninitialised value was created by a stack allocation
# at 0x434B36B2: ??? (in /usr/lib/x86_64-linux-gnu/libavcodec.so.53.35.0)
{
Bug 1248365: FastConvertYUVToRGB32Row-1
Memcheck:Value8
fun:FastConvertYUVToRGB32Row
fun:_ZN7mozilla3gfx19ConvertYCbCrToRGB32*
fun:_ZN7mozilla3gfx17ConvertYCbCrToRGB*
fun:_ZN7mozilla6layers16PlanarYCbCrImage18GetAsSourceSurface*
}
# This is probably a V false positive, due to an insufficiently accurate
# description of the ioctl(SIOCETHTOOL) behavior.
# Syscall param ioctl(SIOCETHTOOL) points to uninitialised byte(s)
# at 0x5D5CBF7: ioctl (syscall-template.S:82)
# by 0xF58EB67: nr_stun_get_addrs (in /home/worker/workspace/build/applica
# by 0xF594791: nr_stun_find_local_addresses (in /home/worker/workspace/bu
# by 0xF58A237: nr_ice_get_local_addresses (in /home/worker/workspace/buil
# by 0xF58ADDE: nr_ice_gather (in /home/worker/workspace/build/application
# by 0xE43F35F: mozilla::NrIceCtx::StartGathering() (in /home/worker/works
# by 0xE419560: mozilla::PeerConnectionMedia::EnsureIceGathering_s() (in /
# by 0xE41A11C: mozilla::runnable_args_memfn<RefPtr<mozilla::PeerConnectio
# Address 0x1cc3fb48 is on thread 6's stack
# in frame #1, created by nr_stun_get_addrs (???:)
{
Bug 1248365: mochitest-ioctl(SIOCETHTOOL)-1
Memcheck:Param
ioctl(SIOCETHTOOL)
fun:ioctl
fun:nr_stun_get_addrs
fun:nr_stun_find_local_addresses
}
# This looks like uninitialised padding bytes in a structure owned
# by libfontconfig. So there's nothing we can do about it.
# Syscall param write(buf) points to uninitialised byte(s)
# at 0x4E44CCD: ??? (syscall-template.S:82)
# by 0x9F1FF56: ??? (in /usr/lib/x86_64-linux-gnu/libfontconfig.so.1.4.4)
# by 0x9F2679B: ??? (in /usr/lib/x86_64-linux-gnu/libfontconfig.so.1.4.4)
# by 0x9F22B98: ??? (in /usr/lib/x86_64-linux-gnu/libfontconfig.so.1.4.4)
# by 0x9F22C5F: FcConfigAppFontAddDir (in /usr/lib/x86_64-linux-gnu/libfon
# by 0xE850173: gfxFcPlatformFontList::ActivateBundledFonts() (in /home/wo
# by 0xE852258: gfxFcPlatformFontList::InitFontListForPlatform() (in /home
# by 0xE895E21: gfxPlatformFontList::InitFontList() (in /home/worker/works
# Address 0x2316663c is 156 bytes inside a block of size 1,448 alloc'd
# at 0x4C2CF71: malloc (vg_replace_malloc.c:299)
# by 0x9F1FD1D: ??? (in /usr/lib/x86_64-linux-gnu/libfontconfig.so.1.4.4)
# by 0x9F26788: ??? (in /usr/lib/x86_64-linux-gnu/libfontconfig.so.1.4.4)
# by 0x9F22B98: ??? (in /usr/lib/x86_64-linux-gnu/libfontconfig.so.1.4.4)
# by 0x9F22C5F: FcConfigAppFontAddDir (in /usr/lib/x86_64-linux-gnu/libfon
# by 0xE850173: gfxFcPlatformFontList::ActivateBundledFonts() (in /home/wo
# by 0xE852258: gfxFcPlatformFontList::InitFontListForPlatform() (in /home
# by 0xE895E21: gfxPlatformFontList::InitFontList() (in /home/worker/works
{
Bug 1248365: libfontconfig-1
Memcheck:Param
write(buf)
obj:/*/libpthread*.so*
obj:/*/libfontconfig.so*
...
obj:/*/libfontconfig.so*
fun:FcConfigAppFontAddDir
}
# There's nothing we can do about this short of throwing in
# --show-mismatched-frees=no, but that's a bit drastic, so for now,
# just suppress it.
#
# Mismatched free() / delete / delete []
# at 0x4C2BE97: free (vg_replace_malloc.c:530)
# by 0xFCD09EC: ots::ots_post_free(ots::Font*) (in /home/worker/workspace/
# by 0xFCC600E: ots::Font::~Font() (in /home/worker/workspace/build/applic
# by 0xFCCBFA5: ots::OTSContext::Process(ots::OTSStream*, unsigned char co
# by 0xE7D7C8D: gfxUserFontEntry::SanitizeOpenTypeData(unsigned char const
# by 0xE7E371D: gfxUserFontEntry::LoadPlatformFont(unsigned char const*, u
# by 0xE7E48AA: gfxUserFontEntry::FontDataDownloadComplete(unsigned char c
# by 0xF49D25B: nsFontFaceLoader::OnStreamComplete(nsIStreamLoader*, nsISu
# Address 0x15671f00 is 0 bytes inside a block of size 490 alloc'd
# at 0x4C2CAEE: operator new(unsigned long) (vg_replace_malloc.c:332)
# by 0xF6AB737: std::vector<unsigned short, std::allocator<unsigned short>
# by 0xFCD0FDE: ots::ots_post_parse(ots::Font*, unsigned char const*, unsi
# by 0xFCCA3D9: (anonymous namespace)::ProcessGeneric(ots::OpenTypeFile*,
# by 0xFCCB17E: (anonymous namespace)::ProcessTTF(ots::OpenTypeFile*, ots:
# by 0xFCCBA54: ots::OTSContext::Process(ots::OTSStream*, unsigned char co
# by 0xE7D7C8D: gfxUserFontEntry::SanitizeOpenTypeData(unsigned char const
# by 0xE7E371D: gfxUserFontEntry::LoadPlatformFont(unsigned char const*, u
{
Bug 1248365: ots::Font::~Font()-1
Memcheck:Free
fun:free
fun:_ZN3ots13ots_post_free*
fun:_ZN3ots4FontD1Ev
fun:_ZN3ots10OTSContext7Process*
}

View File

@ -8,7 +8,7 @@
ifndef NO_DIST_INSTALL
ifneq (,$(strip $(PROGRAM)$(SIMPLE_PROGRAMS)))
PROGRAMS_EXECUTABLES = $(SIMPLE_PROGRAMS) $(PROGRAM)
PROGRAMS_EXECUTABLES = $(SIMPLE_PROGRAMS) $(PROGRAM) $(RUST_PROGRAMS)
PROGRAMS_DEST ?= $(FINAL_TARGET)
PROGRAMS_TARGET := target
INSTALL_TARGETS += PROGRAMS
@ -31,7 +31,7 @@ INSTALL_TARGETS += SHARED_LIBRARY
endif # SHARED_LIBRARY
ifneq (,$(strip $(HOST_SIMPLE_PROGRAMS)$(HOST_PROGRAM)))
HOST_PROGRAMS_EXECUTABLES = $(HOST_SIMPLE_PROGRAMS) $(HOST_PROGRAM)
HOST_PROGRAMS_EXECUTABLES = $(HOST_SIMPLE_PROGRAMS) $(HOST_PROGRAM) $(HOST_RUST_PROGRAMS)
HOST_PROGRAMS_DEST ?= $(DIST)/host/bin
HOST_PROGRAMS_TARGET = host
INSTALL_TARGETS += HOST_PROGRAMS

View File

@ -547,9 +547,9 @@ OBJ_TARGETS = $(OBJS) $(PROGOBJS) $(HOST_OBJS) $(HOST_PROGOBJS)
compile:: host target
host:: $(HOST_LIBRARY) $(HOST_PROGRAM) $(HOST_SIMPLE_PROGRAMS)
host:: $(HOST_LIBRARY) $(HOST_PROGRAM) $(HOST_SIMPLE_PROGRAMS) $(HOST_RUST_PROGRAMS)
target:: $(LIBRARY) $(SHARED_LIBRARY) $(PROGRAM) $(SIMPLE_PROGRAMS) $(RUST_LIBRARY_FILE)
target:: $(LIBRARY) $(SHARED_LIBRARY) $(PROGRAM) $(SIMPLE_PROGRAMS) $(RUST_LIBRARY_FILE) $(RUST_PROGRAMS)
include $(MOZILLA_DIR)/config/makefiles/target_binaries.mk
endif
@ -906,7 +906,8 @@ $(ASOBJS):
endif
ifdef MOZ_RUST
ifdef RUST_LIBRARY_FILE
cargo_host_flag := --target=$(RUST_HOST_TARGET)
cargo_target_flag := --target=$(RUST_TARGET)
# Permit users to pass flags to cargo from their mozconfigs (e.g. --color=always).
cargo_build_flags = $(CARGOFLAGS)
@ -918,7 +919,6 @@ cargo_build_flags += --frozen
endif
cargo_build_flags += --manifest-path $(CARGO_FILE)
cargo_build_flags += --target=$(RUST_TARGET)
cargo_build_flags += --verbose
# Enable color output if original stdout was a TTY and color settings
@ -942,17 +942,34 @@ ifndef MOZ_OPTIMIZE
rustflags_override = RUSTFLAGS='-C opt-level=0'
endif
ifdef RUST_LIBRARY_FILE
# Assume any system libraries rustc links against are already in the target's LIBS.
#
# We need to run cargo unconditionally, because cargo is the only thing that
# has full visibility into how changes in Rust sources might affect the final
# build.
force-cargo-build:
force-cargo-library-build:
$(REPORT_BUILD)
env $(rustflags_override) CARGO_TARGET_DIR=. RUSTC=$(RUSTC) $(CARGO) build $(cargo_build_flags) --
env $(rustflags_override) CARGO_TARGET_DIR=. RUSTC=$(RUSTC) $(CARGO) build --lib $(cargo_build_flags) $(cargo_target_flag) --
$(RUST_LIBRARY_FILE): force-cargo-build
endif # CARGO_FILE
$(RUST_LIBRARY_FILE): force-cargo-library-build
endif # RUST_LIBRARY_FILE
ifdef RUST_PROGRAMS
force-cargo-program-build:
$(REPORT_BUILD)
env $(rustflags_override) CARGO_TARGET_DIR=. RUSTC=$(RUSTC) $(CARGO) build $(addprefix --bin ,$(RUST_CARGO_PROGRAMS)) $(cargo_build_flags) $(cargo_target_flag) --
$(RUST_PROGRAMS): force-cargo-program-build
endif # RUST_PROGRAMS
ifdef HOST_RUST_PROGRAMS
force-cargo-host-program-build:
$(REPORT_BUILD)
env $(rustflags_override) CARGO_TARGET_DIR=. RUSTC=$(RUSTC) $(CARGO) build $(addprefix --bin ,$(HOST_RUST_CARGO_PROGRAMS)) $(cargo_build_flags) $(cargo_host_flag) --
$(HOST_RUST_PROGRAMS): force-cargo-host-program-build
endif # HOST_RUST_PROGRAMS
endif # MOZ_RUST
$(SOBJS):

View File

@ -17,7 +17,6 @@ const {PrefObserver, PREF_ORIG_SOURCES} = require("devtools/client/styleeditor/u
const {createChild} = require("devtools/client/inspector/shared/utils");
const {gDevTools} = require("devtools/client/framework/devtools");
const {getCssProperties} = require("devtools/shared/fronts/css-properties");
const HighlightersOverlay = require("devtools/client/inspector/shared/highlighters-overlay");
const {
VIEW_NODE_SELECTOR_TYPE,
VIEW_NODE_PROPERTY_TYPE,
@ -152,6 +151,7 @@ UpdateProcess.prototype = {
*/
function CssComputedView(inspector, document, pageStyle) {
this.inspector = inspector;
this.highlighters = inspector.highlighters;
this.styleDocument = document;
this.styleWindow = this.styleDocument.defaultView;
this.pageStyle = pageStyle;
@ -216,8 +216,7 @@ function CssComputedView(inspector, document, pageStyle) {
this.tooltips = new TooltipsOverlay(this);
this.tooltips.addToView();
this.highlighters = new HighlightersOverlay(this);
this.highlighters.addToView();
this.highlighters.addToView(this);
}
/**
@ -753,7 +752,7 @@ CssComputedView.prototype = {
}
this.tooltips.destroy();
this.highlighters.destroy();
this.highlighters.removeFromView(this);
// Remove bound listeners
this.styleDocument.removeEventListener("mousedown", this.focusWindow);
@ -781,6 +780,7 @@ CssComputedView.prototype = {
this.propertyViews = null;
this.inspector = null;
this.highlighters = null;
this.styleDocument = null;
this.styleWindow = null;

View File

@ -24,14 +24,15 @@ const Telemetry = require("devtools/client/shared/telemetry");
const Menu = require("devtools/client/framework/menu");
const MenuItem = require("devtools/client/framework/menu-item");
const {CommandUtils} = require("devtools/client/shared/developer-toolbar");
const {HTMLBreadcrumbs} = require("devtools/client/inspector/breadcrumbs");
const {ComputedViewTool} = require("devtools/client/inspector/computed/computed");
const {FontInspector} = require("devtools/client/inspector/fonts/fonts");
const {HTMLBreadcrumbs} = require("devtools/client/inspector/breadcrumbs");
const {InspectorSearch} = require("devtools/client/inspector/inspector-search");
const MarkupView = require("devtools/client/inspector/markup/markup");
const {RuleViewTool} = require("devtools/client/inspector/rules/rules");
const HighlightersOverlay = require("devtools/client/inspector/shared/highlighters-overlay");
const {ToolSidebar} = require("devtools/client/inspector/toolsidebar");
const MarkupView = require("devtools/client/inspector/markup/markup");
const {CommandUtils} = require("devtools/client/shared/developer-toolbar");
const {ViewHelpers} = require("devtools/client/shared/widgets/view-helpers");
const clipboardHelper = require("devtools/shared/platform/clipboard");
@ -92,6 +93,7 @@ function Inspector(toolbox) {
this.panelWin = window;
this.panelWin.inspector = this;
this.highlighters = new HighlightersOverlay(this);
this.telemetry = new Telemetry();
this.nodeMenuTriggerInfo = null;
@ -911,13 +913,19 @@ Inspector.prototype = {
this.breadcrumbs.destroy();
this.selection.off("new-node-front", this.onNewSelection);
this.selection.off("detached-front", this.onDetached);
let markupDestroyer = this._destroyMarkup();
this.panelWin.inspector = null;
this.target = null;
this.panelDoc = null;
this.panelWin = null;
this.breadcrumbs = null;
this._toolbox = null;
this.highlighters.destroy();
this.highlighters = null;
this.search.destroy();
this.search = null;
this.searchBox = null;

View File

@ -19,7 +19,6 @@ const {Rule} = require("devtools/client/inspector/rules/models/rule");
const {RuleEditor} = require("devtools/client/inspector/rules/views/rule-editor");
const {gDevTools} = require("devtools/client/framework/devtools");
const {getCssProperties} = require("devtools/shared/fronts/css-properties");
const HighlightersOverlay = require("devtools/client/inspector/shared/highlighters-overlay");
const {
VIEW_NODE_SELECTOR_TYPE,
VIEW_NODE_PROPERTY_TYPE,
@ -100,6 +99,7 @@ const FILTER_STRICT_RE = /\s*`(.*?)`\s*$/;
*/
function CssRuleView(inspector, document, store, pageStyle) {
this.inspector = inspector;
this.highlighters = inspector.highlighters;
this.styleDocument = document;
this.styleWindow = this.styleDocument.defaultView;
this.store = store || {};
@ -177,8 +177,8 @@ function CssRuleView(inspector, document, store, pageStyle) {
// Add the tooltips and highlighters to the view
this.tooltips = new TooltipsOverlay(this);
this.tooltips.addToView();
this.highlighters = new HighlightersOverlay(this);
this.highlighters.addToView();
this.highlighters.addToView(this);
EventEmitter.decorate(this);
}
@ -252,49 +252,37 @@ CssRuleView.prototype = {
* @param {String} selector
* The selector used to find nodes in the page.
*/
toggleSelectorHighlighter: function (selectorIcon, selector) {
toggleSelectorHighlighter: Task.async(function* (selectorIcon, selector) {
if (this.lastSelectorIcon) {
this.lastSelectorIcon.classList.remove("highlighted");
}
selectorIcon.classList.remove("highlighted");
this.unhighlightSelector().then(() => {
if (selector !== this.highlighters.selectorHighlighterShown) {
this.highlighters.selectorHighlighterShown = selector;
selectorIcon.classList.add("highlighted");
this.lastSelectorIcon = selectorIcon;
this.highlightSelector(selector).then(() => {
this.emit("ruleview-selectorhighlighter-toggled", true);
}, e => console.error(e));
} else {
this.highlighters.selectorHighlighterShown = null;
this.emit("ruleview-selectorhighlighter-toggled", false);
}
}, e => console.error(e));
},
highlightSelector: Task.async(function* (selector) {
let highlighter = yield this.getSelectorHighlighter();
if (!highlighter) {
return;
}
let node = this.inspector.selection.nodeFront;
yield highlighter.show(node, {
hideInfoBar: true,
hideGuides: true,
selector
});
}),
unhighlightSelector: Task.async(function* () {
let highlighter = yield this.getSelectorHighlighter();
if (!highlighter) {
return;
}
yield highlighter.hide();
if (selector !== this.highlighters.selectorHighlighterShown) {
this.highlighters.selectorHighlighterShown = selector;
selectorIcon.classList.add("highlighted");
this.lastSelectorIcon = selectorIcon;
let node = this.inspector.selection.nodeFront;
yield highlighter.show(node, {
hideInfoBar: true,
hideGuides: true,
selector
});
this.emit("ruleview-selectorhighlighter-toggled", true);
} else {
this.highlighters.selectorHighlighterShown = null;
this.emit("ruleview-selectorhighlighter-toggled", false);
}
}),
/**
@ -683,7 +671,7 @@ CssRuleView.prototype = {
}
this.tooltips.destroy();
this.highlighters.destroy();
this.highlighters.removeFromView(this);
// Remove bound listeners
this.shortcuts.destroy();
@ -709,6 +697,7 @@ CssRuleView.prototype = {
this.focusCheckbox = null;
this.inspector = null;
this.highlighters = null;
this.styleDocument = null;
this.styleWindow = null;

View File

@ -16,18 +16,18 @@ const EventEmitter = require("devtools/shared/event-emitter");
const { VIEW_NODE_VALUE_TYPE } = require("devtools/client/inspector/shared/node-types");
/**
* Manages all highlighters in the style-inspector.
* Highlighters overlay is a singleton managing all highlighters in the Inspector.
*
* @param {CssRuleView|CssComputedView} view
* Either the rule-view or computed-view panel
* @param {Inspector} inspector
* Inspector toolbox panel.
*/
function HighlightersOverlay(view) {
this.view = view;
let {CssRuleView} = require("devtools/client/inspector/rules/rules");
this.isRuleView = view instanceof CssRuleView;
function HighlightersOverlay(inspector) {
this.inspector = inspector;
this.highlighters = {};
this.highlighterUtils = this.inspector.toolbox.highlighterUtils;
// Only initialize the overlay if at least one of the highlighter types is supported.
this.supportsHighlighters = this.highlighterUtils.supportsCustomHighlighters();
// NodeFront of the grid container that is highlighted.
this.gridHighlighterShown = null;
@ -36,13 +36,6 @@ function HighlightersOverlay(view) {
// Name of the selector highlighter shown.
this.selectorHighlighterShown = null;
this.highlighterUtils = this.view.inspector.toolbox.highlighterUtils;
// Only initialize the overlay if at least one of the highlighter types is
// supported.
this.supportsHighlighters =
this.highlighterUtils.supportsCustomHighlighters();
this._onClick = this._onClick.bind(this);
this._onMouseMove = this._onMouseMove.bind(this);
this._onMouseOut = this._onMouseOut.bind(this);
@ -52,59 +45,63 @@ function HighlightersOverlay(view) {
}
HighlightersOverlay.prototype = {
get isRuleView() {
return this.inspector.sidebar.getCurrentTabID() == "ruleview";
},
/**
* Add the highlighters overlay to the view. This will start tracking mouse
* movements and display highlighters when needed.
* Add the highlighters overlay to the view. This will start tracking mouse events
* and display highlighters when needed.
*
* @param {CssRuleView|CssComputedView|LayoutView} view
* Either the rule-view or computed-view panel to add the highlighters overlay.
*
*/
addToView: function () {
if (!this.supportsHighlighters || this._isStarted || this._isDestroyed) {
addToView: function (view) {
if (!this.supportsHighlighters) {
return;
}
let el = this.view.element;
let el = view.element;
el.addEventListener("click", this._onClick, true);
el.addEventListener("mousemove", this._onMouseMove, false);
el.addEventListener("mouseout", this._onMouseOut, false);
el.ownerDocument.defaultView.addEventListener("mouseout", this._onMouseOut, false);
if (this.isRuleView) {
this.view.inspector.target.on("will-navigate", this._onWillNavigate);
}
this._isStarted = true;
this.inspector.target.on("will-navigate", this._onWillNavigate);
},
/**
* Remove the overlay from the current view. This will stop tracking mouse
* movement and showing highlighters.
* Remove the overlay from the given view. This will stop tracking mouse movement and
* showing highlighters.
*
* @param {CssRuleView|CssComputedView|LayoutView} view
* Either the rule-view or computed-view panel to remove the highlighters
* overlay.
*/
removeFromView: function () {
if (!this.supportsHighlighters || !this._isStarted || this._isDestroyed) {
removeFromView: function (view) {
if (!this.supportsHighlighters) {
return;
}
let el = this.view.element;
let el = view.element;
el.removeEventListener("click", this._onClick, true);
el.removeEventListener("mousemove", this._onMouseMove, false);
el.removeEventListener("mouseout", this._onMouseOut, false);
if (this.isRuleView) {
this.view.inspector.target.off("will-navigate", this._onWillNavigate);
}
this._isStarted = false;
this.inspector.target.off("will-navigate", this._onWillNavigate);
},
_onClick: function (event) {
// Bail out if the target is not a grid property value.
if (!this._isDisplayGridValue(event.target)) {
if (!this._isRuleViewDisplayGrid(event.target)) {
return;
}
event.stopPropagation();
this._getHighlighter("CssGridHighlighter").then(highlighter => {
let node = this.view.inspector.selection.nodeFront;
let node = this.inspector.selection.nodeFront;
// Toggle off the grid highlighter if the grid highlighter toggle is clicked
// for the current highlighted grid.
@ -115,12 +112,13 @@ HighlightersOverlay.prototype = {
return highlighter.show(node);
}).then(isGridShown => {
// Toggle all the grid icons in the current rule view.
for (let gridIcon of this.view.element.querySelectorAll(".ruleview-grid")) {
let ruleViewEl = this.inspector.ruleview.view.element;
for (let gridIcon of ruleViewEl.querySelectorAll(".ruleview-grid")) {
gridIcon.classList.toggle("active", isGridShown);
}
if (isGridShown) {
this.gridHighlighterShown = this.view.inspector.selection.nodeFront;
this.gridHighlighterShown = this.inspector.selection.nodeFront;
this.emit("highlighter-shown");
} else {
this.gridHighlighterShown = null;
@ -140,7 +138,9 @@ HighlightersOverlay.prototype = {
this._lastHovered = event.target;
let nodeInfo = this.view.getNodeInfo(event.target);
let view = this.isRuleView ?
this.inspector.ruleview.view : this.inspector.computedview.computedView;
let nodeInfo = view.getNodeInfo(event.target);
if (!nodeInfo) {
return;
}
@ -154,7 +154,7 @@ HighlightersOverlay.prototype = {
if (type) {
this.hoveredHighlighterShown = type;
let node = this.view.inspector.selection.nodeFront;
let node = this.inspector.selection.nodeFront;
this._getHighlighter(type)
.then(highlighter => highlighter.show(node))
.then(shown => {
@ -221,7 +221,7 @@ HighlightersOverlay.prototype = {
* @param {DOMNode} node
* @return {Boolean}
*/
_isDisplayGridValue: function (node) {
_isRuleViewDisplayGrid: function (node) {
return this.isRuleView && node.classList.contains("ruleview-grid");
},
@ -289,8 +289,6 @@ HighlightersOverlay.prototype = {
* all initialized highlighters.
*/
destroy: function () {
this.removeFromView();
for (let type in this.highlighters) {
if (this.highlighters[type]) {
this.highlighters[type].finalize();
@ -298,17 +296,13 @@ HighlightersOverlay.prototype = {
}
}
this.inspector = null;
this.highlighters = null;
this.highlighterUtils = null;
this.supportsHighlighters = null;
this.gridHighlighterShown = null;
this.hoveredHighlighterShown = null;
this.selectorHighlighterShown = null;
this.highlighterUtils = null;
this.isRuleView = null;
this.view = null;
this._isDestroyed = true;
}
};

View File

@ -4,7 +4,8 @@
"use strict";
// Test that the css transform highlighter is created only when asked
// Test that the css transform highlighter is created only when asked and only one
// instance exists across the inspector
const TEST_URI = `
<style type="text/css">
@ -37,12 +38,8 @@ add_task(function* () {
yield onComputedViewReady;
overlay = cView.highlighters;
ok(!overlay.highlighters[TYPE], "No highlighter exists in the computed-view");
h = yield overlay._getHighlighter(TYPE);
ok(overlay.highlighters[TYPE],
"The highlighter has been created in the computed-view");
is(h, overlay.highlighters[TYPE], "The right highlighter has been created");
h2 = yield overlay._getHighlighter(TYPE);
is(h, h2, "The same instance of highlighter is returned everytime " +
ok(overlay.highlighters[TYPE], "The highlighter exists in the computed-view");
let h3 = yield overlay._getHighlighter(TYPE);
is(h, h3, "The same instance of highlighter is returned everytime " +
"in the computed-view");
});

View File

@ -42,16 +42,21 @@ add_task(function* () {
yield onComputedViewReady;
hs = cView.highlighters;
ok(!hs.highlighters[TYPE], "No highlighter exists in the computed-view (1)");
info("Remove the created transform highlighter");
hs.highlighters[TYPE].finalize();
hs.highlighters[TYPE] = null;
info("Faking a mousemove on a non-transform property");
({valueSpan} = getComputedViewProperty(cView, "color"));
hs._onMouseMove({target: valueSpan});
ok(!hs.highlighters[TYPE], "No highlighter exists in the computed-view (2)");
ok(!hs.highlighters[TYPE], "No highlighter exists in the computed-view (3)");
info("Faking a mousemove on a transform property");
({valueSpan} = getComputedViewProperty(cView, "transform"));
onHighlighterShown = hs.once("highlighter-shown");
hs._onMouseMove({target: valueSpan});
yield onHighlighterShown;
ok(hs.highlighters[TYPE],
"The highlighter has been created in the computed-view");
});

View File

@ -52,6 +52,7 @@
@media (max-width: 700px) {
#toolbar-spacer,
#details-pane-toggle,
#details-pane.pane-collapsed,
.requests-menu-waterfall,
#requests-menu-network-summary-button > .summary-info-text {
display: none;

View File

@ -613,7 +613,7 @@ AudioChannelService::RefreshAgentsVolumeAndPropagate(AudioChannel aAudioChannel,
void
AudioChannelService::RefreshAgents(nsPIDOMWindowOuter* aWindow,
mozilla::function<void(AudioChannelAgent*)> aFunc)
std::function<void(AudioChannelAgent*)> aFunc)
{
MOZ_ASSERT(aWindow);
MOZ_ASSERT(aWindow->IsOuterWindow());

View File

@ -16,7 +16,8 @@
#include "AudioChannelAgent.h"
#include "nsAttrValue.h"
#include "mozilla/dom/AudioChannelBinding.h"
#include "mozilla/Function.h"
#include <functional>
class nsIRunnable;
class nsPIDOMWindowOuter;
@ -195,7 +196,7 @@ private:
~AudioChannelService();
void RefreshAgents(nsPIDOMWindowOuter* aWindow,
mozilla::function<void(AudioChannelAgent*)> aFunc);
std::function<void(AudioChannelAgent*)> aFunc);
static void CreateServiceIfNeeded();

View File

@ -158,6 +158,32 @@ NS_INTERFACE_MAP_END
NS_IMPL_CYCLE_COLLECTING_ADDREF(Blob)
NS_IMPL_CYCLE_COLLECTING_RELEASE(Blob)
// A utility function that enforces the spec constraints on the type of a blob:
// no codepoints outside the ASCII range (otherwise type becomes empty) and
// lowercase ASCII only. We can't just use our existing nsContentUtils
// ASCII-related helpers because we need the "outside ASCII range" check, and we
// can't use NS_IsAscii because its definition of "ASCII" (chars all <= 0x7E)
// differs from the file API definition (which excludes control chars).
static void
MakeValidBlobType(nsAString& aType)
{
char16_t* iter = aType.BeginWriting();
char16_t* end = aType.EndWriting();
for ( ; iter != end; ++iter) {
char16_t c = *iter;
if (c < 0x20 || c > 0x7E) {
// Non-ASCII char, bail out.
aType.Truncate();
return;
}
if (c >= 'A' && c <= 'Z') {
*iter = c + ('a' - 'A');
}
}
}
/* static */ Blob*
Blob::Create(nsISupports* aParent, BlobImpl* aImpl)
{
@ -167,26 +193,6 @@ Blob::Create(nsISupports* aParent, BlobImpl* aImpl)
: new Blob(aParent, aImpl);
}
/* static */ already_AddRefed<Blob>
Blob::Create(nsISupports* aParent, const nsAString& aContentType,
uint64_t aLength)
{
RefPtr<Blob> blob = Blob::Create(aParent,
new BlobImplBase(aContentType, aLength));
MOZ_ASSERT(!blob->mImpl->IsFile());
return blob.forget();
}
/* static */ already_AddRefed<Blob>
Blob::Create(nsISupports* aParent, const nsAString& aContentType,
uint64_t aStart, uint64_t aLength)
{
RefPtr<Blob> blob = Blob::Create(aParent,
new BlobImplBase(aContentType, aStart, aLength));
MOZ_ASSERT(!blob->mImpl->IsFile());
return blob.forget();
}
/* static */ already_AddRefed<Blob>
Blob::CreateStringBlob(nsISupports* aParent, const nsACString& aData,
const nsAString& aContentType)
@ -360,7 +366,9 @@ Blob::Constructor(const GlobalObject& aGlobal,
RefPtr<MultipartBlobImpl> impl = new MultipartBlobImpl();
if (aData.WasPassed()) {
impl->InitializeBlob(aGlobal.Context(), aData.Value(), aBag.mType,
nsAutoString type(aBag.mType);
MakeValidBlobType(type);
impl->InitializeBlob(aGlobal.Context(), aData.Value(), type,
aBag.mEndings == EndingTypes::Native, aRv);
} else {
impl->InitializeBlob(aRv);
@ -549,7 +557,9 @@ File::Constructor(const GlobalObject& aGlobal,
{
RefPtr<MultipartBlobImpl> impl = new MultipartBlobImpl(aName);
impl->InitializeBlob(aGlobal.Context(), aData, aBag.mType, false, aRv);
nsAutoString type(aBag.mType);
MakeValidBlobType(type);
impl->InitializeBlob(aGlobal.Context(), aData, type, false, aRv);
if (aRv.Failed()) {
return nullptr;
}
@ -640,8 +650,9 @@ BlobImpl::Slice(const Optional<int64_t>& aStart,
ParseSize((int64_t)thisLength, start, end);
return CreateSlice((uint64_t)start, (uint64_t)(end - start),
aContentType, aRv);
nsAutoString type(aContentType);
MakeValidBlobType(type);
return CreateSlice((uint64_t)start, (uint64_t)(end - start), type, aRv);
}
////////////////////////////////////////////////////////////////////////////

View File

@ -64,14 +64,6 @@ public:
static Blob*
Create(nsISupports* aParent, BlobImpl* aImpl);
static already_AddRefed<Blob>
Create(nsISupports* aParent, const nsAString& aContentType,
uint64_t aLength);
static already_AddRefed<Blob>
Create(nsISupports* aParent, const nsAString& aContentType, uint64_t aStart,
uint64_t aLength);
static already_AddRefed<Blob>
CreateStringBlob(nsISupports* aParent, const nsACString& aData,
const nsAString& aContentType);

View File

@ -6,7 +6,6 @@
#include "IdleRequest.h"
#include "mozilla/Function.h"
#include "mozilla/TimeStamp.h"
#include "mozilla/dom/IdleDeadline.h"
#include "mozilla/dom/Performance.h"

View File

@ -119,21 +119,19 @@ public:
bool IsTargetThread() const;
void Init(JSContext* aCx,
nsIPrincipal* aPrincipal,
bool aIsServerSide,
const nsAString& aURL,
nsTArray<nsString>& aProtocolArray,
const nsACString& aScriptFile,
uint32_t aScriptLine,
uint32_t aScriptColumn,
ErrorResult& aRv,
bool* aConnectionFailed);
nsresult Init(JSContext* aCx,
nsIPrincipal* aPrincipal,
bool aIsServerSide,
const nsAString& aURL,
nsTArray<nsString>& aProtocolArray,
const nsACString& aScriptFile,
uint32_t aScriptLine,
uint32_t aScriptColumn,
bool* aConnectionFailed);
void AsyncOpen(nsIPrincipal* aPrincipal, uint64_t aInnerWindowID,
nsITransportProvider* aTransportProvider,
const nsACString& aNegotiatedExtensions,
ErrorResult& aRv);
nsresult AsyncOpen(nsIPrincipal* aPrincipal, uint64_t aInnerWindowID,
nsITransportProvider* aTransportProvider,
const nsACString& aNegotiatedExtensions);
nsresult ParseURL(const nsAString& aURL);
nsresult InitializeConnection(nsIPrincipal* aPrincipal);
@ -1064,8 +1062,7 @@ public:
const nsAString& aURL,
nsTArray<nsString>& aProtocolArray,
const nsACString& aScriptFile, uint32_t aScriptLine,
uint32_t aScriptColumn,
ErrorResult& aRv, bool* aConnectionFailed)
uint32_t aScriptColumn, bool* aConnectionFailed)
: WebSocketMainThreadRunnable(aImpl->mWorkerPrivate,
NS_LITERAL_CSTRING("WebSocket :: init"))
, mImpl(aImpl)
@ -1075,19 +1072,25 @@ public:
, mScriptFile(aScriptFile)
, mScriptLine(aScriptLine)
, mScriptColumn(aScriptColumn)
, mRv(aRv)
, mConnectionFailed(aConnectionFailed)
, mErrorCode(NS_OK)
{
MOZ_ASSERT(mWorkerPrivate);
mWorkerPrivate->AssertIsOnWorkerThread();
}
nsresult
ErrorCode() const
{
return mErrorCode;
}
protected:
virtual bool InitWithWindow(nsPIDOMWindowInner* aWindow) override
{
AutoJSAPI jsapi;
if (NS_WARN_IF(!jsapi.Init(aWindow))) {
mRv.Throw(NS_ERROR_FAILURE);
mErrorCode = NS_ERROR_FAILURE;
return true;
}
@ -1095,19 +1098,19 @@ protected:
nsIDocument* doc = aWindow->GetExtantDoc();
if (!doc) {
mRv.Throw(NS_ERROR_FAILURE);
mErrorCode = NS_ERROR_FAILURE;
return true;
}
nsCOMPtr<nsIPrincipal> principal = doc->NodePrincipal();
if (!principal) {
mRv.Throw(NS_ERROR_FAILURE);
mErrorCode = NS_ERROR_FAILURE;
return true;
}
mImpl->Init(jsapi.cx(), principal, mIsServerSide, mURL, mProtocolArray,
mScriptFile, mScriptLine, mScriptColumn, mRv,
mConnectionFailed);
mErrorCode =
mImpl->Init(jsapi.cx(), principal, mIsServerSide, mURL, mProtocolArray,
mScriptFile, mScriptLine, mScriptColumn, mConnectionFailed);
return true;
}
@ -1116,9 +1119,10 @@ protected:
MOZ_ASSERT(NS_IsMainThread());
MOZ_ASSERT(aTopLevelWorkerPrivate && !aTopLevelWorkerPrivate->GetWindow());
mImpl->Init(nullptr, aTopLevelWorkerPrivate->GetPrincipal(), mIsServerSide,
mURL, mProtocolArray, mScriptFile, mScriptLine, mScriptColumn,
mRv, mConnectionFailed);
mErrorCode =
mImpl->Init(nullptr, aTopLevelWorkerPrivate->GetPrincipal(),
mIsServerSide, mURL, mProtocolArray, mScriptFile, mScriptLine,
mScriptColumn, mConnectionFailed);
return true;
}
@ -1131,23 +1135,29 @@ protected:
nsCString mScriptFile;
uint32_t mScriptLine;
uint32_t mScriptColumn;
ErrorResult& mRv;
bool* mConnectionFailed;
nsresult mErrorCode;
};
class AsyncOpenRunnable final : public WebSocketMainThreadRunnable
{
public:
AsyncOpenRunnable(WebSocketImpl* aImpl, ErrorResult& aRv)
explicit AsyncOpenRunnable(WebSocketImpl* aImpl)
: WebSocketMainThreadRunnable(aImpl->mWorkerPrivate,
NS_LITERAL_CSTRING("WebSocket :: AsyncOpen"))
, mImpl(aImpl)
, mRv(aRv)
, mErrorCode(NS_OK)
{
MOZ_ASSERT(mWorkerPrivate);
mWorkerPrivate->AssertIsOnWorkerThread();
}
nsresult
ErrorCode() const
{
return mErrorCode;
}
protected:
virtual bool InitWithWindow(nsPIDOMWindowInner* aWindow) override
{
@ -1156,13 +1166,13 @@ protected:
nsIDocument* doc = aWindow->GetExtantDoc();
if (!doc) {
mRv.Throw(NS_ERROR_FAILURE);
mErrorCode = NS_ERROR_FAILURE;
return true;
}
nsCOMPtr<nsIPrincipal> principal = doc->NodePrincipal();
if (!principal) {
mRv.Throw(NS_ERROR_FAILURE);
mErrorCode = NS_ERROR_FAILURE;
return true;
}
@ -1177,7 +1187,7 @@ protected:
windowID = topInner->WindowID();
}
mImpl->AsyncOpen(principal, windowID, nullptr, EmptyCString(), mRv);
mErrorCode = mImpl->AsyncOpen(principal, windowID, nullptr, EmptyCString());
return true;
}
@ -1186,8 +1196,9 @@ protected:
MOZ_ASSERT(NS_IsMainThread());
MOZ_ASSERT(aTopLevelWorkerPrivate && !aTopLevelWorkerPrivate->GetWindow());
mImpl->AsyncOpen(aTopLevelWorkerPrivate->GetPrincipal(), 0, nullptr,
EmptyCString(), mRv);
mErrorCode =
mImpl->AsyncOpen(aTopLevelWorkerPrivate->GetPrincipal(), 0, nullptr,
EmptyCString());
return true;
}
@ -1195,7 +1206,7 @@ private:
// Raw pointer. This worker runs synchronously.
WebSocketImpl* mImpl;
ErrorResult& mRv;
nsresult mErrorCode;
};
} // namespace
@ -1270,9 +1281,10 @@ WebSocket::ConstructorCommon(const GlobalObject& aGlobal,
bool connectionFailed = true;
if (NS_IsMainThread()) {
webSocketImpl->Init(aGlobal.Context(), principal, !!aTransportProvider,
aUrl, protocolArray, EmptyCString(),
0, 0, aRv, &connectionFailed);
aRv =
webSocketImpl->Init(aGlobal.Context(), principal, !!aTransportProvider,
aUrl, protocolArray, EmptyCString(), 0, 0,
&connectionFailed);
} else {
// In workers we have to keep the worker alive using a workerHolder in order
// to dispatch messages correctly.
@ -1291,8 +1303,13 @@ WebSocket::ConstructorCommon(const GlobalObject& aGlobal,
RefPtr<InitRunnable> runnable =
new InitRunnable(webSocketImpl, !!aTransportProvider, aUrl,
protocolArray, nsDependentCString(file.get()), lineno,
column, aRv, &connectionFailed);
column, &connectionFailed);
runnable->Dispatch(aRv);
if (NS_WARN_IF(aRv.Failed())) {
return nullptr;
}
aRv = runnable->ErrorCode();
}
if (NS_WARN_IF(aRv.Failed())) {
@ -1369,14 +1386,19 @@ WebSocket::ConstructorCommon(const GlobalObject& aGlobal,
windowID = topInner->WindowID();
}
webSocket->mImpl->AsyncOpen(principal, windowID, aTransportProvider,
aNegotiatedExtensions, aRv);
aRv = webSocket->mImpl->AsyncOpen(principal, windowID, aTransportProvider,
aNegotiatedExtensions);
} else {
MOZ_ASSERT(!aTransportProvider && aNegotiatedExtensions.IsEmpty(),
"not yet implemented");
RefPtr<AsyncOpenRunnable> runnable =
new AsyncOpenRunnable(webSocket->mImpl, aRv);
new AsyncOpenRunnable(webSocket->mImpl);
runnable->Dispatch(aRv);
if (NS_WARN_IF(aRv.Failed())) {
return nullptr;
}
aRv = runnable->ErrorCode();
}
if (NS_WARN_IF(aRv.Failed())) {
@ -1467,7 +1489,7 @@ WebSocket::DisconnectFromOwner()
// WebSocketImpl:: initialization
//-----------------------------------------------------------------------------
void
nsresult
WebSocketImpl::Init(JSContext* aCx,
nsIPrincipal* aPrincipal,
bool aIsServerSide,
@ -1476,7 +1498,6 @@ WebSocketImpl::Init(JSContext* aCx,
const nsACString& aScriptFile,
uint32_t aScriptLine,
uint32_t aScriptColumn,
ErrorResult& aRv,
bool* aConnectionFailed)
{
AssertIsOnMainThread();
@ -1489,29 +1510,22 @@ WebSocketImpl::Init(JSContext* aCx,
RefPtr<WebSocketImpl> kungfuDeathGrip = this;
// Attempt to kill "ghost" websocket: but usually too early for check to fail
aRv = mWebSocket->CheckInnerWindowCorrectness();
if (NS_WARN_IF(aRv.Failed())) {
return;
}
nsresult rv = mWebSocket->CheckInnerWindowCorrectness();
NS_ENSURE_SUCCESS(rv, rv);
// Shut down websocket if window is frozen or destroyed (only needed for
// "ghost" websockets--see bug 696085)
if (!mWorkerPrivate) {
nsCOMPtr<nsIObserverService> os = mozilla::services::GetObserverService();
if (NS_WARN_IF(!os)) {
aRv.Throw(NS_ERROR_FAILURE);
return;
return NS_ERROR_FAILURE;
}
aRv = os->AddObserver(this, DOM_WINDOW_DESTROYED_TOPIC, true);
if (NS_WARN_IF(aRv.Failed())) {
return;
}
rv = os->AddObserver(this, DOM_WINDOW_DESTROYED_TOPIC, true);
NS_ENSURE_SUCCESS(rv, rv);
aRv = os->AddObserver(this, DOM_WINDOW_FROZEN_TOPIC, true);
if (NS_WARN_IF(aRv.Failed())) {
return;
}
rv = os->AddObserver(this, DOM_WINDOW_FROZEN_TOPIC, true);
NS_ENSURE_SUCCESS(rv, rv);
}
if (mWorkerPrivate) {
@ -1540,18 +1554,13 @@ WebSocketImpl::Init(JSContext* aCx,
}
// parses the url
aRv = ParseURL(PromiseFlatString(aURL));
if (NS_WARN_IF(aRv.Failed())) {
return;
}
rv = ParseURL(PromiseFlatString(aURL));
NS_ENSURE_SUCCESS(rv, rv);
nsCOMPtr<nsIDocument> originDoc = mWebSocket->GetDocumentIfCurrent();
if (!originDoc) {
nsresult rv = mWebSocket->CheckInnerWindowCorrectness();
if (NS_WARN_IF(NS_FAILED(rv))) {
aRv.Throw(rv);
return;
}
rv = mWebSocket->CheckInnerWindowCorrectness();
NS_ENSURE_SUCCESS(rv, rv);
}
mOriginDocument = do_GetWeakReference(originDoc);
@ -1574,24 +1583,20 @@ WebSocketImpl::Init(JSContext* aCx,
// Please note that websockets can't follow redirects, hence there is no
// need to perform a CSP check after redirects.
int16_t shouldLoad = nsIContentPolicy::ACCEPT;
aRv = NS_CheckContentLoadPolicy(nsIContentPolicy::TYPE_WEBSOCKET,
uri,
aPrincipal,
originDoc,
EmptyCString(),
nullptr,
&shouldLoad,
nsContentUtils::GetContentPolicy(),
nsContentUtils::GetSecurityManager());
if (NS_WARN_IF(aRv.Failed())) {
return;
}
rv = NS_CheckContentLoadPolicy(nsIContentPolicy::TYPE_WEBSOCKET,
uri,
aPrincipal,
originDoc,
EmptyCString(),
nullptr,
&shouldLoad,
nsContentUtils::GetContentPolicy(),
nsContentUtils::GetSecurityManager());
NS_ENSURE_SUCCESS(rv, rv);
if (NS_CP_REJECTED(shouldLoad)) {
// Disallowed by content policy
aRv.Throw(NS_ERROR_CONTENT_BLOCKED);
return;
return NS_ERROR_CONTENT_BLOCKED;
}
}
@ -1608,7 +1613,7 @@ WebSocketImpl::Init(JSContext* aCx,
// upgrade the request from ws:// to wss:// and mark as secure
mURI.ReplaceSubstring("ws://", "wss://");
if (NS_WARN_IF(mURI.Find("wss://") != 0)) {
return;
return NS_OK;
}
mSecure = true;
@ -1656,23 +1661,20 @@ WebSocketImpl::Init(JSContext* aCx,
if (!innerWindow) {
innerWindow = do_QueryInterface(globalObject);
if (NS_WARN_IF(!innerWindow)) {
aRv.Throw(NS_ERROR_DOM_SECURITY_ERR);
return;
return NS_ERROR_DOM_SECURITY_ERR;
}
}
nsCOMPtr<nsPIDOMWindowOuter> parentWindow =
innerWindow->GetScriptableParent();
if (NS_WARN_IF(!parentWindow)) {
aRv.Throw(NS_ERROR_DOM_SECURITY_ERR);
return;
return NS_ERROR_DOM_SECURITY_ERR;
}
nsCOMPtr<nsPIDOMWindowInner> currentInnerWindow =
parentWindow->GetCurrentInnerWindow();
if (NS_WARN_IF(!currentInnerWindow)) {
aRv.Throw(NS_ERROR_DOM_SECURITY_ERR);
return;
return NS_ERROR_DOM_SECURITY_ERR;
}
// We are at the top. Let's see if we have an opener window.
@ -1682,8 +1684,7 @@ WebSocketImpl::Init(JSContext* aCx,
nsGlobalWindow::Cast(innerWindow)->GetOpenerWindow(error);
if (NS_WARN_IF(error.Failed())) {
error.SuppressException();
aRv.Throw(NS_ERROR_DOM_SECURITY_ERR);
return;
return NS_ERROR_DOM_SECURITY_ERR;
}
if (!parentWindow) {
@ -1692,8 +1693,7 @@ WebSocketImpl::Init(JSContext* aCx,
currentInnerWindow = parentWindow->GetCurrentInnerWindow();
if (NS_WARN_IF(!currentInnerWindow)) {
aRv.Throw(NS_ERROR_DOM_SECURITY_ERR);
return;
return NS_ERROR_DOM_SECURITY_ERR;
}
MOZ_ASSERT(currentInnerWindow != innerWindow);
@ -1703,8 +1703,7 @@ WebSocketImpl::Init(JSContext* aCx,
nsCOMPtr<nsIDocument> document = innerWindow->GetExtantDoc();
if (NS_WARN_IF(!document)) {
aRv.Throw(NS_ERROR_DOM_SECURITY_ERR);
return;
return NS_ERROR_DOM_SECURITY_ERR;
}
principal = document->NodePrincipal();
@ -1717,13 +1716,11 @@ WebSocketImpl::Init(JSContext* aCx,
if (originURI) {
bool originIsHttps = false;
aRv = originURI->SchemeIs("https", &originIsHttps);
if (NS_WARN_IF(aRv.Failed())) {
return;
}
rv = originURI->SchemeIs("https", &originIsHttps);
NS_ENSURE_SUCCESS(rv, rv);
if (originIsHttps) {
aRv.Throw(NS_ERROR_DOM_SECURITY_ERR);
return;
return NS_ERROR_DOM_SECURITY_ERR;
}
}
}
@ -1733,8 +1730,7 @@ WebSocketImpl::Init(JSContext* aCx,
for (uint32_t i = 0; i < aProtocolArray[index].Length(); ++i) {
if (aProtocolArray[index][i] < static_cast<char16_t>(0x0021) ||
aProtocolArray[index][i] > static_cast<char16_t>(0x007E)) {
aRv.Throw(NS_ERROR_DOM_SYNTAX_ERR);
return;
return NS_ERROR_DOM_SYNTAX_ERR;
}
}
@ -1753,45 +1749,44 @@ WebSocketImpl::Init(JSContext* aCx,
} else {
*aConnectionFailed = false;
}
return NS_OK;
}
void
nsresult
WebSocketImpl::AsyncOpen(nsIPrincipal* aPrincipal, uint64_t aInnerWindowID,
nsITransportProvider* aTransportProvider,
const nsACString& aNegotiatedExtensions,
ErrorResult& aRv)
const nsACString& aNegotiatedExtensions)
{
MOZ_ASSERT(NS_IsMainThread(), "Not running on main thread");
MOZ_ASSERT_IF(!aTransportProvider, aNegotiatedExtensions.IsEmpty());
nsCString asciiOrigin;
aRv = nsContentUtils::GetASCIIOrigin(aPrincipal, asciiOrigin);
if (NS_WARN_IF(aRv.Failed())) {
return;
}
nsresult rv = nsContentUtils::GetASCIIOrigin(aPrincipal, asciiOrigin);
NS_ENSURE_SUCCESS(rv, rv);
if (aTransportProvider) {
aRv = mChannel->SetServerParameters(aTransportProvider, aNegotiatedExtensions);
if (NS_WARN_IF(aRv.Failed())) {
return;
}
rv = mChannel->SetServerParameters(aTransportProvider,
aNegotiatedExtensions);
NS_ENSURE_SUCCESS(rv, rv);
}
ToLowerCase(asciiOrigin);
nsCOMPtr<nsIURI> uri;
if (!aTransportProvider) {
aRv = NS_NewURI(getter_AddRefs(uri), mURI);
MOZ_ASSERT(!aRv.Failed());
rv = NS_NewURI(getter_AddRefs(uri), mURI);
MOZ_ASSERT(NS_SUCCEEDED(rv));
}
aRv = mChannel->AsyncOpen(uri, asciiOrigin, aInnerWindowID, this, nullptr);
if (NS_WARN_IF(aRv.Failed())) {
aRv.Throw(NS_ERROR_CONTENT_BLOCKED);
return;
rv = mChannel->AsyncOpen(uri, asciiOrigin, aInnerWindowID, this, nullptr);
if (NS_WARN_IF(NS_FAILED(rv))) {
return NS_ERROR_CONTENT_BLOCKED;
}
mInnerWindowID = aInnerWindowID;
return NS_OK;
}
//-----------------------------------------------------------------------------

View File

@ -75,7 +75,12 @@ nsDataDocumentContentPolicy::ShouldLoad(uint32_t aContentType,
}
}
if (doc->IsBeingUsedAsImage()) {
nsIDocument* docToCheckForImage = doc->GetDisplayDocument();
if (!docToCheckForImage) {
docToCheckForImage = doc;
}
if (docToCheckForImage->IsBeingUsedAsImage()) {
// We only allow SVG images to load content from URIs that are local and
// also satisfy one of the following conditions:
// - URI inherits security context, e.g. data URIs

View File

@ -9,7 +9,6 @@
#include "nsITimeoutHandler.h"
#include "nsTArray.h"
#include "js/TypeDecls.h"
#include "mozilla/Function.h"
#include "mozilla/Maybe.h"
namespace mozilla {

View File

@ -7,7 +7,6 @@
#include <algorithm>
#include "mozilla/Attributes.h"
#include "mozilla/Function.h"
#include "mozilla/Likely.h"
#include "mozilla/Maybe.h"
#include "mozilla/dom/FunctionBinding.h"

View File

@ -0,0 +1,19 @@
<!DOCTYPE HTML>
<html>
<body>
<script>
let count = 0;
function cb() {
count += 1;
// Notify our parent that we are ready once the timer flood has
// warmed up.
if (count === 10000) {
window.parent.postMessage('STARTED', '*');
}
setTimeout(cb, 0);
setTimeout(cb, 0);
}
addEventListener('load', cb);
</script>
</body>
</html>

View File

@ -159,6 +159,7 @@ support-files =
file_record_orientation.html
file_restrictedEventSource.sjs
file_simplecontentpolicy.js
file_timer_flood.html
file_websocket_basic_wsh.py
file_websocket_hello_wsh.py
file_websocket_http_resource.txt
@ -672,6 +673,7 @@ skip-if = (toolkit == 'android') # Android: Bug 775227
[test_innersize_scrollport.html]
[test_integer_attr_with_leading_zero.html]
[test_intersectionobservers.html]
skip-if = true # Track Bug 1320704
[test_ipc_messagemanager_blob.html]
[test_link_prefetch.html]
skip-if = !e10s # Track Bug 1281415
@ -764,6 +766,7 @@ skip-if = e10s # Bug 1156489.
[test_text_wholeText.html]
[test_textnode_normalize_in_selection.html]
[test_textnode_split_in_selection.html]
[test_timer_flood.html]
[test_title.html]
[test_treewalker_nextsibling.xml]
[test_user_select.html]

View File

@ -0,0 +1,116 @@
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Test Behavior During Timer Flood</title>
<script type="application/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
<link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css"/>
</head>
<body>
<p id="display"></p>
<div id="content" style="display: none">
</div>
<pre id="test">
<script type="application/javascript">
SimpleTest.waitForExplicitFinish();
function onLoad() {
return new Promise(resolve => {
addEventListener('load', resolve, { once: true });
});
}
// Create a frame that executes a timer flood. The frame signals
// that is ready once the flood has had a chance to warm up.
function withFloodFrame() {
return new Promise(resolve => {
let frame = document.createElement('iframe');
addEventListener('message', function onMsg(evt) {
if (evt.data === 'STARTED') {
removeEventListener('message', onMsg);
resolve(frame);
}
});
frame.src = 'file_timer_flood.html';
document.body.appendChild(frame);
});
}
// Test that we can load documents during a timer flood.
function testFrameLoad() {
return new Promise(resolve => {
let frame = document.createElement('iframe');
frame.addEventListener('load', _ => {
frame.remove();
resolve();
}, { once: true });
document.body.appendChild(frame);
});
}
// Test that we can perform network requests while a timer flood
// is occuring.
function testFetch(url) {
return fetch(url).then(response => {
return response.text();
});
}
// Test that we can run animations for 5 seconds while a timer
// flood is occuring.
function testRequestAnimationFrame() {
return new Promise(resolve => {
let remainingFrames = 5 * 60;
function nextFrame() {
remainingFrames -= 1;
if (remainingFrames > 0) {
requestAnimationFrame(nextFrame);
} else {
resolve();
}
};
requestAnimationFrame(nextFrame);
});
}
let floodFrame;
onLoad().then(_ => {
// Start a timer flood in a frame.
return withFloodFrame();
}).then(frame => {
floodFrame = frame;
// Next we are going to start a bunch of asynchronous work that we
// expect to complete in spite of the timer flood. The type of work
// is a bit arbitrary, but is chosen to reflect the kinds of things
// we would like the browser to be able to do even when pages are
// abusing timers. Feel free to add more types of work here, but
// think carefully before removing anything.
let tests = [];
// Verify we can perform a variety of work while the timer flood
// is running.
for (let i = 0; i < 20; ++i) {
tests.push(testFrameLoad());
tests.push(testFetch('file_timer_flood.html'));
}
// Verify that animations still work while the timer flood is running.
// Note that we do one long run of animations instead of parallel runs
// like the other activities because of the way requestAnimationFrame()
// is scheduled. Parallel animations would not result in any additional
// runnables be placed on the event queue.
tests.push(testRequestAnimationFrame());
// Wait for all tests to finish. If we do not handle the timer flood
// well then this will likely time out.
return Promise.all(tests);
}).then(_ => {
ok(true, 'completed tests without timing out');
floodFrame.remove();
SimpleTest.finish();
});
</script>
</pre>
</body>
</html>

View File

@ -1077,6 +1077,11 @@ DOMInterfaces = {
'headerFile': 'WebGLBuffer.h'
},
'WEBGL_compressed_texture_astc': {
'nativeType': 'mozilla::WebGLExtensionCompressedTextureASTC',
'headerFile': 'WebGLExtensions.h'
},
'WEBGL_compressed_texture_atc': {
'nativeType': 'mozilla::WebGLExtensionCompressedTextureATC',
'headerFile': 'WebGLExtensions.h'

View File

@ -263,10 +263,13 @@ TypeUtils::ToResponse(const CacheResponse& aIn)
RefPtr<InternalHeaders> internalHeaders =
ToInternalHeaders(aIn.headers(), aIn.headersGuard());
ErrorResult result;
ir->Headers()->SetGuard(aIn.headersGuard(), result);
MOZ_ASSERT(!result.Failed());
// Be careful to fill the headers before setting the guard in order to
// correctly re-create the original headers.
ir->Headers()->Fill(*internalHeaders, result);
MOZ_ASSERT(!result.Failed());
ir->Headers()->SetGuard(aIn.headersGuard(), result);
MOZ_ASSERT(!result.Failed());
ir->InitChannelInfo(aIn.channelInfo());
if (aIn.principalInfo().type() == mozilla::ipc::OptionalPrincipalInfo::TPrincipalInfo) {

View File

@ -20,6 +20,7 @@ support-files =
test_cache_requestCache.js
test_cache_delete.js
test_cache_put_reorder.js
test_cache_redirect.js
test_cache_https.js
large_url_list.js
empty.html
@ -37,6 +38,7 @@ support-files =
[test_cache_delete.html]
[test_cache_put_reorder.html]
[test_cache_https.html]
[test_cache_redirect.html]
[test_cache_restart.html]
[test_cache_shrink.html]
[test_cache_orphaned_cache.html]

View File

@ -0,0 +1,20 @@
<!-- Any copyright is dedicated to the Public Domain.
- http://creativecommons.org/publicdomain/zero/1.0/ -->
<!DOCTYPE HTML>
<html>
<head>
<title>Validate Cache storage of redirect responses</title>
<script type="text/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
<link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css" />
<script type="text/javascript" src="driver.js"></script>
</head>
<body>
<iframe id="frame"></iframe>
<script class="testbody" type="text/javascript">
runTests("test_cache_redirect.js")
.then(function() {
SimpleTest.finish();
});
</script>
</body>
</html>

View File

@ -0,0 +1,14 @@
let cache;
let url = 'foo.html';
let redirectURL = 'http://example.com/foo-bar.html';
caches.open('redirect-' + context).then(c => {
cache = c;
var response = Response.redirect(redirectURL);
is(response.headers.get('Location'), redirectURL);
return cache.put(url, response);
}).then(_ => {
return cache.match(url);
}).then(response => {
is(response.headers.get('Location'), redirectURL);
testDone();
});

View File

@ -565,7 +565,7 @@ public:
explicit AdjustedTarget(CanvasRenderingContext2D* aCtx,
const gfx::Rect *aBounds = nullptr)
{
mTarget = aCtx->mTarget;
mTarget = (DrawTarget*)aCtx->mTarget;
// All rects in this function are in the device space of ctx->mTarget.
@ -1720,7 +1720,7 @@ CanvasRenderingContext2D::SetErrorState()
gCanvasAzureMemoryUsed -= mWidth * mHeight * 4;
}
mTarget = sErrorTarget;
mTarget = (DrawTarget*)sErrorTarget;
mBufferProvider = nullptr;
// clear transforms, clips, etc.
@ -1975,7 +1975,7 @@ CanvasRenderingContext2D::InitializeWithDrawTarget(nsIDocShell* aShell,
IntSize size = aTarget->GetSize();
SetDimensions(size.width, size.height);
mTarget = aTarget;
mTarget = (DrawTarget*)aTarget;
mBufferProvider = new PersistentBufferProviderBasic(aTarget);
if (mTarget->GetBackendType() == gfx::BackendType::CAIRO) {
@ -3154,6 +3154,8 @@ CanvasRenderingContext2D::BeginPath()
void
CanvasRenderingContext2D::Fill(const CanvasWindingRule& aWinding)
{
auto autoNotNull = mTarget.MakeAuto();
EnsureUserSpacePath(aWinding);
if (!mPath) {
@ -4758,6 +4760,8 @@ CanvasRenderingContext2D::DrawImage(const CanvasImageSource& aImage,
uint8_t aOptional_argc,
ErrorResult& aError)
{
auto autoNotNull = mTarget.MakeAuto();
if (mDrawObserver) {
mDrawObserver->DidDrawCall(CanvasDrawObserver::DrawCallType::DrawImage);
}
@ -5019,7 +5023,7 @@ CanvasRenderingContext2D::DrawImage(const CanvasImageSource& aImage,
AdjustedTarget tempTarget(this, bounds.IsEmpty() ? nullptr : &bounds);
if (!tempTarget) {
gfxDevCrash(LogReason::InvalidDrawTarget) << "Invalid adjusted target in Canvas2D " << gfx::hexa(mTarget) << ", " << NeedToDrawShadow() << NeedToApplyFilter();
gfxDevCrash(LogReason::InvalidDrawTarget) << "Invalid adjusted target in Canvas2D " << gfx::hexa((DrawTarget*)mTarget) << ", " << NeedToDrawShadow() << NeedToApplyFilter();
return;
}
tempTarget->DrawSurface(srcSurf,

View File

@ -47,6 +47,118 @@ class TextMetrics;
class CanvasFilterChainObserver;
class CanvasPath;
template<class T>
struct MaybeNotNull
{
MOZ_IMPLICIT MaybeNotNull() : mWrapped(nullptr), mEnsure(false) {}
MOZ_IMPLICIT MaybeNotNull(T&& aValue) : mWrapped(aValue), mEnsure(false) {}
~MaybeNotNull() {}
void BeginNotNull() {
mEnsure = true;
}
void EndNotNull() {
mEnsure = false;
}
void MaybeCheckWrapped() {
if (mEnsure && !mWrapped) {
MOZ_CRASH("GFX: Setting mTarget to nullptr?");
}
}
typename T::element_type* operator->() const {
return mWrapped.get();
}
already_AddRefed<typename T::element_type> forget() {
already_AddRefed<typename T::element_type>&& ret = mWrapped.forget();
MaybeCheckWrapped();
return Move(ret);
}
MOZ_IMPLICIT operator bool () {
return mWrapped;
}
operator T&() {
return mWrapped;
}
operator typename T::element_type*() {
return mWrapped.get();
}
bool operator!() const {
return !mWrapped;
}
MaybeNotNull& operator=(decltype(nullptr)) {
mWrapped = nullptr;
MaybeCheckWrapped();
return *this;
}
template<class U>
MaybeNotNull& operator=(U& aOther){
mWrapped = aOther;
MaybeCheckWrapped();
return *this;
}
template<class U>
MaybeNotNull& operator=(U&& aOther){
mWrapped = aOther;
MaybeCheckWrapped();
return *this;
}
struct AutoNotNull
{
MOZ_IMPLICIT AutoNotNull(MaybeNotNull* aMaybe) : mMaybe(aMaybe)
{
mMaybe->BeginNotNull();
}
~AutoNotNull()
{
mMaybe->EndNotNull();
}
MaybeNotNull* mMaybe;
};
AutoNotNull MakeAuto()
{
return AutoNotNull(this);
}
T mWrapped;
bool mEnsure;
};
template<class T, class U>
bool operator!=(const MaybeNotNull<T>& aT, const U& aU) {
return aT.mWrapped != aU;
}
template<class T, class U>
bool operator==(const MaybeNotNull<T>& aT, const U& aU) {
return aT.mWrapped == aU;
}
template<class T, class U>
bool operator||(const MaybeNotNull<T>& aT, const U& aU) {
return aT.mWrapped || aU;
}
template<class T, class U>
bool operator||(const T& aT, const MaybeNotNull<U>& aU) {
return aT || aU.mWrapped;
}
extern const mozilla::gfx::Float SIGMA_MAX;
template<typename T> class Optional;
@ -686,7 +798,7 @@ protected:
* Check if the target is valid after calling EnsureTarget.
*/
bool IsTargetValid() const {
return mTarget && mTarget != sErrorTarget;
return !!mTarget && mTarget != sErrorTarget;
}
/**
@ -771,7 +883,7 @@ protected:
// This is created lazily so it is necessary to call EnsureTarget before
// accessing it. In the event of an error it will be equal to
// sErrorTarget.
RefPtr<mozilla::gfx::DrawTarget> mTarget;
MaybeNotNull<RefPtr<mozilla::gfx::DrawTarget>> mTarget;
RefPtr<mozilla::layers::PersistentBufferProvider> mBufferProvider;

View File

@ -9,9 +9,10 @@
#include "ImageContainer.h"
#include "libyuv.h"
#include "mozilla/dom/ImageBitmapBinding.h"
#include "mozilla/Function.h"
#include "mozilla/gfx/2D.h"
#include <functional>
using namespace libyuv;
using namespace mozilla::gfx;
@ -325,7 +326,7 @@ static UniquePtr<ImagePixelLayout>
CvtSimpleImgToSimpleImg(Utils* aSrcUtils, const SrcType* aSrcBuffer,
const ImagePixelLayout* aSrcLayout, DstType* aDstBuffer,
ImageBitmapFormat aDstFormat, int aDstChannelCount,
mozilla::function<int (const SrcType*, int, DstType*, int, int, int)> converter)
std::function<int (const SrcType*, int, DstType*, int, int, int)> converter)
{
MOZ_ASSERT(aSrcUtils, "Convert color from a null utility object.");
MOZ_ASSERT(aSrcBuffer, "Convert color from a null buffer.");
@ -353,7 +354,7 @@ static UniquePtr<ImagePixelLayout>
CvtYUVImgToSimpleImg(Utils* aSrcUtils, const uint8_t* aSrcBuffer,
const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer,
ImageBitmapFormat aDstFormat, int aDstChannelCount,
mozilla::function<int (const uint8_t*, int, const uint8_t*, int, const uint8_t*, int, uint8_t*, int, int, int)> converter)
std::function<int (const uint8_t*, int, const uint8_t*, int, const uint8_t*, int, uint8_t*, int, int, int)> converter)
{
MOZ_ASSERT(aSrcUtils, "Convert color from a null utility object.");
MOZ_ASSERT(aSrcBuffer, "Convert color from a null buffer.");
@ -383,7 +384,7 @@ static UniquePtr<ImagePixelLayout>
CvtNVImgToSimpleImg(Utils* aSrcUtils, const uint8_t* aSrcBuffer,
const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer,
ImageBitmapFormat aDstFormat, int aDstChannelCount,
mozilla::function<int (const uint8_t*, int, const uint8_t*, int, uint8_t*, int, int, int)> converter)
std::function<int (const uint8_t*, int, const uint8_t*, int, uint8_t*, int, int, int)> converter)
{
MOZ_ASSERT(aSrcUtils, "Convert color from a null utility object.");
MOZ_ASSERT(aSrcBuffer, "Convert color from a null buffer.");
@ -412,7 +413,7 @@ static UniquePtr<ImagePixelLayout>
CvtSimpleImgToYUVImg(Utils* aSrcUtils, const uint8_t* aSrcBuffer,
const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer,
ImageBitmapFormat aDstFormat,
mozilla::function<int (const uint8_t*, int, uint8_t*, int, uint8_t*, int, uint8_t*, int, int, int)> converter)
std::function<int (const uint8_t*, int, uint8_t*, int, uint8_t*, int, uint8_t*, int, int, int)> converter)
{
MOZ_ASSERT(aSrcUtils, "Convert color from a null utility object.");
MOZ_ASSERT(aSrcBuffer, "Convert color from a null buffer.");
@ -444,7 +445,7 @@ static UniquePtr<ImagePixelLayout>
CvtSimpleImgToNVImg(Utils* aSrcUtils, const uint8_t* aSrcBuffer,
const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer,
ImageBitmapFormat aDstFormat,
mozilla::function<int (const uint8_t*, int, uint8_t*, int, uint8_t*, int, int, int)> converter)
std::function<int (const uint8_t*, int, uint8_t*, int, uint8_t*, int, int, int)> converter)
{
MOZ_ASSERT(aSrcUtils, "Convert color from a null utility object.");
MOZ_ASSERT(aSrcBuffer, "Convert color from a null buffer.");

View File

@ -273,6 +273,7 @@ class WebGLContext
friend class ScopedFBRebinder;
friend class WebGL2Context;
friend class WebGLContextUserData;
friend class WebGLExtensionCompressedTextureASTC;
friend class WebGLExtensionCompressedTextureATC;
friend class WebGLExtensionCompressedTextureES3;
friend class WebGLExtensionCompressedTextureETC1;

View File

@ -48,6 +48,7 @@ WebGLContext::GetExtensionString(WebGLExtensionID ext)
WEBGL_EXTENSION_IDENTIFIER(OES_texture_half_float_linear)
WEBGL_EXTENSION_IDENTIFIER(OES_vertex_array_object)
WEBGL_EXTENSION_IDENTIFIER(WEBGL_color_buffer_float)
WEBGL_EXTENSION_IDENTIFIER(WEBGL_compressed_texture_astc)
WEBGL_EXTENSION_IDENTIFIER(WEBGL_compressed_texture_atc)
WEBGL_EXTENSION_IDENTIFIER(WEBGL_compressed_texture_etc)
WEBGL_EXTENSION_IDENTIFIER(WEBGL_compressed_texture_etc1)
@ -122,6 +123,8 @@ WebGLContext::IsExtensionSupported(WebGLExtensionID ext) const
return gl->IsSupported(gl::GLFeature::texture_float_linear);
// WEBGL_
case WebGLExtensionID::WEBGL_compressed_texture_astc:
return WebGLExtensionCompressedTextureASTC::IsSupported(this);
case WebGLExtensionID::WEBGL_compressed_texture_atc:
return gl->IsExtensionSupported(gl::GLContext::AMD_compressed_ATC_texture);
case WebGLExtensionID::WEBGL_compressed_texture_etc:
@ -399,6 +402,9 @@ WebGLContext::EnableExtension(WebGLExtensionID ext)
case WebGLExtensionID::WEBGL_color_buffer_float:
obj = new WebGLExtensionColorBufferFloat(this);
break;
case WebGLExtensionID::WEBGL_compressed_texture_astc:
obj = new WebGLExtensionCompressedTextureASTC(this);
break;
case WebGLExtensionID::WEBGL_compressed_texture_atc:
obj = new WebGLExtensionCompressedTextureATC(this);
break;

View File

@ -0,0 +1,95 @@
/* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this file,
* You can obtain one at http://mozilla.org/MPL/2.0/. */
#include "WebGLExtensions.h"
#include "GLContext.h"
#include "mozilla/dom/WebGLRenderingContextBinding.h"
#include "WebGLContext.h"
namespace mozilla {
WebGLExtensionCompressedTextureASTC::WebGLExtensionCompressedTextureASTC(WebGLContext* webgl)
: WebGLExtensionBase(webgl)
{
MOZ_ASSERT(IsSupported(webgl), "Don't construct extension if unsupported.");
RefPtr<WebGLContext> webgl_ = webgl; // Bug 1201275
const auto fnAdd = [&webgl_](GLenum sizedFormat, webgl::EffectiveFormat effFormat) {
auto& fua = webgl_->mFormatUsage;
auto usage = fua->EditUsage(effFormat);
usage->isFilterable = true;
fua->AllowSizedTexFormat(sizedFormat, usage);
webgl_->mCompressedTextureFormats.AppendElement(sizedFormat);
};
#define FOO(x) LOCAL_GL_ ## x, webgl::EffectiveFormat::x
fnAdd(FOO(COMPRESSED_RGBA_ASTC_4x4_KHR));
fnAdd(FOO(COMPRESSED_RGBA_ASTC_5x4_KHR));
fnAdd(FOO(COMPRESSED_RGBA_ASTC_5x5_KHR));
fnAdd(FOO(COMPRESSED_RGBA_ASTC_6x5_KHR));
fnAdd(FOO(COMPRESSED_RGBA_ASTC_6x6_KHR));
fnAdd(FOO(COMPRESSED_RGBA_ASTC_8x5_KHR));
fnAdd(FOO(COMPRESSED_RGBA_ASTC_8x6_KHR));
fnAdd(FOO(COMPRESSED_RGBA_ASTC_8x8_KHR));
fnAdd(FOO(COMPRESSED_RGBA_ASTC_10x5_KHR));
fnAdd(FOO(COMPRESSED_RGBA_ASTC_10x6_KHR));
fnAdd(FOO(COMPRESSED_RGBA_ASTC_10x8_KHR));
fnAdd(FOO(COMPRESSED_RGBA_ASTC_10x10_KHR));
fnAdd(FOO(COMPRESSED_RGBA_ASTC_12x10_KHR));
fnAdd(FOO(COMPRESSED_RGBA_ASTC_12x12_KHR));
fnAdd(FOO(COMPRESSED_SRGB8_ALPHA8_ASTC_4x4_KHR));
fnAdd(FOO(COMPRESSED_SRGB8_ALPHA8_ASTC_5x4_KHR));
fnAdd(FOO(COMPRESSED_SRGB8_ALPHA8_ASTC_5x5_KHR));
fnAdd(FOO(COMPRESSED_SRGB8_ALPHA8_ASTC_6x5_KHR));
fnAdd(FOO(COMPRESSED_SRGB8_ALPHA8_ASTC_6x6_KHR));
fnAdd(FOO(COMPRESSED_SRGB8_ALPHA8_ASTC_8x5_KHR));
fnAdd(FOO(COMPRESSED_SRGB8_ALPHA8_ASTC_8x6_KHR));
fnAdd(FOO(COMPRESSED_SRGB8_ALPHA8_ASTC_8x8_KHR));
fnAdd(FOO(COMPRESSED_SRGB8_ALPHA8_ASTC_10x5_KHR));
fnAdd(FOO(COMPRESSED_SRGB8_ALPHA8_ASTC_10x6_KHR));
fnAdd(FOO(COMPRESSED_SRGB8_ALPHA8_ASTC_10x8_KHR));
fnAdd(FOO(COMPRESSED_SRGB8_ALPHA8_ASTC_10x10_KHR));
fnAdd(FOO(COMPRESSED_SRGB8_ALPHA8_ASTC_12x10_KHR));
fnAdd(FOO(COMPRESSED_SRGB8_ALPHA8_ASTC_12x12_KHR));
#undef FOO
}
WebGLExtensionCompressedTextureASTC::~WebGLExtensionCompressedTextureASTC()
{
}
void
WebGLExtensionCompressedTextureASTC::GetSupportedProfiles(dom::Nullable< nsTArray<nsString> >& retval) const
{
retval.SetNull();
if (mIsLost) {
mContext->ErrorInvalidOperation("%s: Extension is lost.",
"drawElementsInstancedANGLE");
return;
}
nsTArray<nsString>& arr = retval.SetValue();
arr.AppendElement(NS_LITERAL_STRING("ldr"));
if (mContext->gl->IsExtensionSupported(gl::GLContext::KHR_texture_compression_astc_hdr)) {
arr.AppendElement(NS_LITERAL_STRING("hdr"));
}
}
bool
WebGLExtensionCompressedTextureASTC::IsSupported(const WebGLContext* webgl)
{
gl::GLContext* gl = webgl->GL();
return gl->IsExtensionSupported(gl::GLContext::KHR_texture_compression_astc_ldr);
}
IMPL_WEBGL_EXTENSION_GOOP(WebGLExtensionCompressedTextureASTC, WEBGL_compressed_texture_astc)
} // namespace mozilla

View File

@ -7,6 +7,8 @@
#define WEBGL_EXTENSIONS_H_
#include "mozilla/AlreadyAddRefed.h"
#include "nsString.h"
#include "nsTArray.h"
#include "nsWrapperCache.h"
#include "WebGLObjectModel.h"
#include "WebGLTypes.h"
@ -14,8 +16,8 @@
namespace mozilla {
namespace dom {
template<typename T>
class Sequence;
template<typename> struct Nullable;
template<typename> class Sequence;
} // namespace dom
namespace webgl {
@ -60,6 +62,22 @@ protected:
return dom::WebGLBindingType##Binding::Wrap(cx, this, givenProto); \
}
////
class WebGLExtensionCompressedTextureASTC
: public WebGLExtensionBase
{
public:
explicit WebGLExtensionCompressedTextureASTC(WebGLContext* webgl);
virtual ~WebGLExtensionCompressedTextureASTC();
void GetSupportedProfiles(dom::Nullable< nsTArray<nsString> >& retval) const;
static bool IsSupported(const WebGLContext* webgl);
DECL_WEBGL_EXTENSION_GOOP
};
class WebGLExtensionCompressedTextureATC
: public WebGLExtensionBase
{

View File

@ -113,6 +113,37 @@ InitCompressedFormatInfo()
AddCompressedFormatInfo(EffectiveFormat::COMPRESSED_RGBA_S3TC_DXT3_EXT, 128, 4, 4, CompressionFamily::S3TC);
AddCompressedFormatInfo(EffectiveFormat::COMPRESSED_RGBA_S3TC_DXT5_EXT, 128, 4, 4, CompressionFamily::S3TC);
// KHR_texture_compression_astc_ldr
AddCompressedFormatInfo(EffectiveFormat::COMPRESSED_RGBA_ASTC_4x4_KHR , 128, 4, 4, CompressionFamily::ASTC);
AddCompressedFormatInfo(EffectiveFormat::COMPRESSED_RGBA_ASTC_5x4_KHR , 128, 5, 4, CompressionFamily::ASTC);
AddCompressedFormatInfo(EffectiveFormat::COMPRESSED_RGBA_ASTC_5x5_KHR , 128, 5, 5, CompressionFamily::ASTC);
AddCompressedFormatInfo(EffectiveFormat::COMPRESSED_RGBA_ASTC_6x5_KHR , 128, 6, 5, CompressionFamily::ASTC);
AddCompressedFormatInfo(EffectiveFormat::COMPRESSED_RGBA_ASTC_6x6_KHR , 128, 6, 6, CompressionFamily::ASTC);
AddCompressedFormatInfo(EffectiveFormat::COMPRESSED_RGBA_ASTC_8x5_KHR , 128, 8, 5, CompressionFamily::ASTC);
AddCompressedFormatInfo(EffectiveFormat::COMPRESSED_RGBA_ASTC_8x6_KHR , 128, 8, 6, CompressionFamily::ASTC);
AddCompressedFormatInfo(EffectiveFormat::COMPRESSED_RGBA_ASTC_8x8_KHR , 128, 8, 8, CompressionFamily::ASTC);
AddCompressedFormatInfo(EffectiveFormat::COMPRESSED_RGBA_ASTC_10x5_KHR , 128, 10, 5, CompressionFamily::ASTC);
AddCompressedFormatInfo(EffectiveFormat::COMPRESSED_RGBA_ASTC_10x6_KHR , 128, 10, 6, CompressionFamily::ASTC);
AddCompressedFormatInfo(EffectiveFormat::COMPRESSED_RGBA_ASTC_10x8_KHR , 128, 10, 8, CompressionFamily::ASTC);
AddCompressedFormatInfo(EffectiveFormat::COMPRESSED_RGBA_ASTC_10x10_KHR , 128, 10, 10, CompressionFamily::ASTC);
AddCompressedFormatInfo(EffectiveFormat::COMPRESSED_RGBA_ASTC_12x10_KHR , 128, 12, 10, CompressionFamily::ASTC);
AddCompressedFormatInfo(EffectiveFormat::COMPRESSED_RGBA_ASTC_12x12_KHR , 128, 12, 12, CompressionFamily::ASTC);
AddCompressedFormatInfo(EffectiveFormat::COMPRESSED_SRGB8_ALPHA8_ASTC_4x4_KHR , 128, 4, 4, CompressionFamily::ASTC);
AddCompressedFormatInfo(EffectiveFormat::COMPRESSED_SRGB8_ALPHA8_ASTC_5x4_KHR , 128, 5, 4, CompressionFamily::ASTC);
AddCompressedFormatInfo(EffectiveFormat::COMPRESSED_SRGB8_ALPHA8_ASTC_5x5_KHR , 128, 5, 5, CompressionFamily::ASTC);
AddCompressedFormatInfo(EffectiveFormat::COMPRESSED_SRGB8_ALPHA8_ASTC_6x5_KHR , 128, 6, 5, CompressionFamily::ASTC);
AddCompressedFormatInfo(EffectiveFormat::COMPRESSED_SRGB8_ALPHA8_ASTC_6x6_KHR , 128, 6, 6, CompressionFamily::ASTC);
AddCompressedFormatInfo(EffectiveFormat::COMPRESSED_SRGB8_ALPHA8_ASTC_8x5_KHR , 128, 8, 5, CompressionFamily::ASTC);
AddCompressedFormatInfo(EffectiveFormat::COMPRESSED_SRGB8_ALPHA8_ASTC_8x6_KHR , 128, 8, 6, CompressionFamily::ASTC);
AddCompressedFormatInfo(EffectiveFormat::COMPRESSED_SRGB8_ALPHA8_ASTC_8x8_KHR , 128, 8, 8, CompressionFamily::ASTC);
AddCompressedFormatInfo(EffectiveFormat::COMPRESSED_SRGB8_ALPHA8_ASTC_10x5_KHR , 128, 10, 5, CompressionFamily::ASTC);
AddCompressedFormatInfo(EffectiveFormat::COMPRESSED_SRGB8_ALPHA8_ASTC_10x6_KHR , 128, 10, 6, CompressionFamily::ASTC);
AddCompressedFormatInfo(EffectiveFormat::COMPRESSED_SRGB8_ALPHA8_ASTC_10x8_KHR , 128, 10, 8, CompressionFamily::ASTC);
AddCompressedFormatInfo(EffectiveFormat::COMPRESSED_SRGB8_ALPHA8_ASTC_10x10_KHR, 128, 10, 10, CompressionFamily::ASTC);
AddCompressedFormatInfo(EffectiveFormat::COMPRESSED_SRGB8_ALPHA8_ASTC_12x10_KHR, 128, 12, 10, CompressionFamily::ASTC);
AddCompressedFormatInfo(EffectiveFormat::COMPRESSED_SRGB8_ALPHA8_ASTC_12x12_KHR, 128, 12, 12, CompressionFamily::ASTC);
// IMG_texture_compression_pvrtc
AddCompressedFormatInfo(EffectiveFormat::COMPRESSED_RGB_PVRTC_4BPPV1 , 256, 8, 8, CompressionFamily::PVRTC);
AddCompressedFormatInfo(EffectiveFormat::COMPRESSED_RGBA_PVRTC_4BPPV1, 256, 8, 8, CompressionFamily::PVRTC);
@ -292,6 +323,37 @@ InitFormatInfo()
AddFormatInfo(FOO(COMPRESSED_RGBA_S3TC_DXT3_EXT), 0, 1,1,1,1, 0,0, UnsizedFormat::RGBA, false, ComponentType::NormUInt);
AddFormatInfo(FOO(COMPRESSED_RGBA_S3TC_DXT5_EXT), 0, 1,1,1,1, 0,0, UnsizedFormat::RGBA, false, ComponentType::NormUInt);
// KHR_texture_compression_astc_ldr
AddFormatInfo(FOO(COMPRESSED_RGBA_ASTC_4x4_KHR ), 0, 1,1,1,1, 0,0, UnsizedFormat::RGBA, false, ComponentType::NormUInt);
AddFormatInfo(FOO(COMPRESSED_RGBA_ASTC_5x4_KHR ), 0, 1,1,1,1, 0,0, UnsizedFormat::RGBA, false, ComponentType::NormUInt);
AddFormatInfo(FOO(COMPRESSED_RGBA_ASTC_5x5_KHR ), 0, 1,1,1,1, 0,0, UnsizedFormat::RGBA, false, ComponentType::NormUInt);
AddFormatInfo(FOO(COMPRESSED_RGBA_ASTC_6x5_KHR ), 0, 1,1,1,1, 0,0, UnsizedFormat::RGBA, false, ComponentType::NormUInt);
AddFormatInfo(FOO(COMPRESSED_RGBA_ASTC_6x6_KHR ), 0, 1,1,1,1, 0,0, UnsizedFormat::RGBA, false, ComponentType::NormUInt);
AddFormatInfo(FOO(COMPRESSED_RGBA_ASTC_8x5_KHR ), 0, 1,1,1,1, 0,0, UnsizedFormat::RGBA, false, ComponentType::NormUInt);
AddFormatInfo(FOO(COMPRESSED_RGBA_ASTC_8x6_KHR ), 0, 1,1,1,1, 0,0, UnsizedFormat::RGBA, false, ComponentType::NormUInt);
AddFormatInfo(FOO(COMPRESSED_RGBA_ASTC_8x8_KHR ), 0, 1,1,1,1, 0,0, UnsizedFormat::RGBA, false, ComponentType::NormUInt);
AddFormatInfo(FOO(COMPRESSED_RGBA_ASTC_10x5_KHR ), 0, 1,1,1,1, 0,0, UnsizedFormat::RGBA, false, ComponentType::NormUInt);
AddFormatInfo(FOO(COMPRESSED_RGBA_ASTC_10x6_KHR ), 0, 1,1,1,1, 0,0, UnsizedFormat::RGBA, false, ComponentType::NormUInt);
AddFormatInfo(FOO(COMPRESSED_RGBA_ASTC_10x8_KHR ), 0, 1,1,1,1, 0,0, UnsizedFormat::RGBA, false, ComponentType::NormUInt);
AddFormatInfo(FOO(COMPRESSED_RGBA_ASTC_10x10_KHR ), 0, 1,1,1,1, 0,0, UnsizedFormat::RGBA, false, ComponentType::NormUInt);
AddFormatInfo(FOO(COMPRESSED_RGBA_ASTC_12x10_KHR ), 0, 1,1,1,1, 0,0, UnsizedFormat::RGBA, false, ComponentType::NormUInt);
AddFormatInfo(FOO(COMPRESSED_RGBA_ASTC_12x12_KHR ), 0, 1,1,1,1, 0,0, UnsizedFormat::RGBA, false, ComponentType::NormUInt);
AddFormatInfo(FOO(COMPRESSED_SRGB8_ALPHA8_ASTC_4x4_KHR ), 0, 1,1,1,1, 0,0, UnsizedFormat::RGBA, true , ComponentType::NormUInt);
AddFormatInfo(FOO(COMPRESSED_SRGB8_ALPHA8_ASTC_5x4_KHR ), 0, 1,1,1,1, 0,0, UnsizedFormat::RGBA, true , ComponentType::NormUInt);
AddFormatInfo(FOO(COMPRESSED_SRGB8_ALPHA8_ASTC_5x5_KHR ), 0, 1,1,1,1, 0,0, UnsizedFormat::RGBA, true , ComponentType::NormUInt);
AddFormatInfo(FOO(COMPRESSED_SRGB8_ALPHA8_ASTC_6x5_KHR ), 0, 1,1,1,1, 0,0, UnsizedFormat::RGBA, true , ComponentType::NormUInt);
AddFormatInfo(FOO(COMPRESSED_SRGB8_ALPHA8_ASTC_6x6_KHR ), 0, 1,1,1,1, 0,0, UnsizedFormat::RGBA, true , ComponentType::NormUInt);
AddFormatInfo(FOO(COMPRESSED_SRGB8_ALPHA8_ASTC_8x5_KHR ), 0, 1,1,1,1, 0,0, UnsizedFormat::RGBA, true , ComponentType::NormUInt);
AddFormatInfo(FOO(COMPRESSED_SRGB8_ALPHA8_ASTC_8x6_KHR ), 0, 1,1,1,1, 0,0, UnsizedFormat::RGBA, true , ComponentType::NormUInt);
AddFormatInfo(FOO(COMPRESSED_SRGB8_ALPHA8_ASTC_8x8_KHR ), 0, 1,1,1,1, 0,0, UnsizedFormat::RGBA, true , ComponentType::NormUInt);
AddFormatInfo(FOO(COMPRESSED_SRGB8_ALPHA8_ASTC_10x5_KHR ), 0, 1,1,1,1, 0,0, UnsizedFormat::RGBA, true , ComponentType::NormUInt);
AddFormatInfo(FOO(COMPRESSED_SRGB8_ALPHA8_ASTC_10x6_KHR ), 0, 1,1,1,1, 0,0, UnsizedFormat::RGBA, true , ComponentType::NormUInt);
AddFormatInfo(FOO(COMPRESSED_SRGB8_ALPHA8_ASTC_10x8_KHR ), 0, 1,1,1,1, 0,0, UnsizedFormat::RGBA, true , ComponentType::NormUInt);
AddFormatInfo(FOO(COMPRESSED_SRGB8_ALPHA8_ASTC_10x10_KHR), 0, 1,1,1,1, 0,0, UnsizedFormat::RGBA, true , ComponentType::NormUInt);
AddFormatInfo(FOO(COMPRESSED_SRGB8_ALPHA8_ASTC_12x10_KHR), 0, 1,1,1,1, 0,0, UnsizedFormat::RGBA, true , ComponentType::NormUInt);
AddFormatInfo(FOO(COMPRESSED_SRGB8_ALPHA8_ASTC_12x12_KHR), 0, 1,1,1,1, 0,0, UnsizedFormat::RGBA, true , ComponentType::NormUInt);
// IMG_texture_compression_pvrtc
AddFormatInfo(FOO(COMPRESSED_RGB_PVRTC_4BPPV1 ), 0, 1,1,1,0, 0,0, UnsizedFormat::RGB , false, ComponentType::NormUInt);
AddFormatInfo(FOO(COMPRESSED_RGBA_PVRTC_4BPPV1), 0, 1,1,1,1, 0,0, UnsizedFormat::RGBA, false, ComponentType::NormUInt);

View File

@ -119,6 +119,37 @@ enum class EffectiveFormat : EffectiveFormatValueT {
COMPRESSED_RGBA_S3TC_DXT3_EXT,
COMPRESSED_RGBA_S3TC_DXT5_EXT,
// KHR_texture_compression_astc_ldr
COMPRESSED_RGBA_ASTC_4x4_KHR,
COMPRESSED_RGBA_ASTC_5x4_KHR,
COMPRESSED_RGBA_ASTC_5x5_KHR,
COMPRESSED_RGBA_ASTC_6x5_KHR,
COMPRESSED_RGBA_ASTC_6x6_KHR,
COMPRESSED_RGBA_ASTC_8x5_KHR,
COMPRESSED_RGBA_ASTC_8x6_KHR,
COMPRESSED_RGBA_ASTC_8x8_KHR,
COMPRESSED_RGBA_ASTC_10x5_KHR,
COMPRESSED_RGBA_ASTC_10x6_KHR,
COMPRESSED_RGBA_ASTC_10x8_KHR,
COMPRESSED_RGBA_ASTC_10x10_KHR,
COMPRESSED_RGBA_ASTC_12x10_KHR,
COMPRESSED_RGBA_ASTC_12x12_KHR,
COMPRESSED_SRGB8_ALPHA8_ASTC_4x4_KHR,
COMPRESSED_SRGB8_ALPHA8_ASTC_5x4_KHR,
COMPRESSED_SRGB8_ALPHA8_ASTC_5x5_KHR,
COMPRESSED_SRGB8_ALPHA8_ASTC_6x5_KHR,
COMPRESSED_SRGB8_ALPHA8_ASTC_6x6_KHR,
COMPRESSED_SRGB8_ALPHA8_ASTC_8x5_KHR,
COMPRESSED_SRGB8_ALPHA8_ASTC_8x6_KHR,
COMPRESSED_SRGB8_ALPHA8_ASTC_8x8_KHR,
COMPRESSED_SRGB8_ALPHA8_ASTC_10x5_KHR,
COMPRESSED_SRGB8_ALPHA8_ASTC_10x6_KHR,
COMPRESSED_SRGB8_ALPHA8_ASTC_10x8_KHR,
COMPRESSED_SRGB8_ALPHA8_ASTC_10x10_KHR,
COMPRESSED_SRGB8_ALPHA8_ASTC_12x10_KHR,
COMPRESSED_SRGB8_ALPHA8_ASTC_12x12_KHR,
// IMG_texture_compression_pvrtc
COMPRESSED_RGB_PVRTC_4BPPV1,
COMPRESSED_RGBA_PVRTC_4BPPV1,
@ -173,11 +204,12 @@ enum class ComponentType : uint8_t {
};
enum class CompressionFamily : uint8_t {
ETC1,
ES3, // ETC2 or EAC
ASTC,
ATC,
S3TC,
ES3, // ETC2 or EAC
ETC1,
PVRTC,
S3TC,
};
////////////////////////////////////////////////////////////////////////////////

View File

@ -931,6 +931,16 @@ ValidateCompressedTexImageRestrictions(const char* funcName, WebGLContext* webgl
};
switch (format->compression->family) {
case webgl::CompressionFamily::ASTC:
if (target == LOCAL_GL_TEXTURE_3D &&
!webgl->gl->IsExtensionSupported(gl::GLContext::KHR_texture_compression_astc_hdr))
{
webgl->ErrorInvalidOperation("%s: TEXTURE_3D requires ASTC's hdr profile.",
funcName);
return false;
}
break;
case webgl::CompressionFamily::PVRTC:
if (!IsPowerOfTwo(width) || !IsPowerOfTwo(height)) {
webgl->ErrorInvalidValue("%s: %s requires power-of-two width and height.",

View File

@ -157,6 +157,7 @@ enum class WebGLExtensionID : uint8_t {
OES_texture_half_float_linear,
OES_vertex_array_object,
WEBGL_color_buffer_float,
WEBGL_compressed_texture_astc,
WEBGL_compressed_texture_atc,
WEBGL_compressed_texture_etc,
WEBGL_compressed_texture_etc1,

View File

@ -108,6 +108,7 @@ UNIFIED_SOURCES += [
'WebGLExtensionBlendMinMax.cpp',
'WebGLExtensionColorBufferFloat.cpp',
'WebGLExtensionColorBufferHalfFloat.cpp',
'WebGLExtensionCompressedTextureASTC.cpp',
'WebGLExtensionCompressedTextureATC.cpp',
'WebGLExtensionCompressedTextureES3.cpp',
'WebGLExtensionCompressedTextureETC1.cpp',

View File

@ -528,7 +528,9 @@ ExtractFromBlob(const Blob& aBlob,
nsAutoString type;
impl->GetType(type);
aContentType = NS_ConvertUTF16toUTF8(type);
if (!type.IsEmpty()) {
CopyUTF16toUTF8(type, aContentType);
}
return NS_OK;
}
@ -603,6 +605,7 @@ ExtractByteStreamFromBody(const OwningArrayBufferOrArrayBufferViewOrBlobOrFormDa
uint64_t& aContentLength)
{
MOZ_ASSERT(aStream);
aContentType.SetIsVoid(true);
if (aBodyInit.IsArrayBuffer()) {
const ArrayBuffer& buf = aBodyInit.GetAsArrayBuffer();
@ -642,6 +645,7 @@ ExtractByteStreamFromBody(const ArrayBufferOrArrayBufferViewOrBlobOrFormDataOrUS
{
MOZ_ASSERT(aStream);
MOZ_ASSERT(!*aStream);
aContentType.SetIsVoid(true);
if (aBodyInit.IsArrayBuffer()) {
const ArrayBuffer& buf = aBodyInit.GetAsArrayBuffer();

View File

@ -183,7 +183,7 @@ nsresult nsJSThunk::EvaluateScript(nsIChannel *aChannel,
bool allowsInlineScript = true;
rv = csp->GetAllowsInline(nsIContentPolicy::TYPE_SCRIPT,
EmptyString(), // aNonce
false, // aParserCreated
true, // aParserCreated
EmptyString(), // aContent
0, // aLineNumber
&allowsInlineScript);

View File

@ -21,6 +21,9 @@ description_label=Description
suffixes_label=Suffixes
learn_more_label=Learn More
deprecation_description=Missing something? Some plugins are no longer supported.
deprecation_learn_more=Learn More.
# GMP Plugins
gmp_license_info=License information
gmp_privacy_info=Privacy Information

View File

@ -7,7 +7,6 @@
#include "mozilla/Base64.h"
#include "mozilla/TaskQueue.h"
#include "mozilla/Telemetry.h"
#include "mozilla/Function.h"
#include "MediaContentType.h"
#include "MediaPrefs.h"
@ -26,6 +25,7 @@
#include "nsCharSeparatedTokenizer.h"
#include "nsContentTypeParser.h"
#include <functional>
#include <stdint.h>
namespace mozilla {

View File

@ -52,6 +52,8 @@
#include "mp4_demuxer/H264.h"
#include <functional>
namespace mozilla {
extern already_AddRefed<PlatformDecoderModule> CreateAgnosticDecoderModule();
@ -155,7 +157,7 @@ public:
void Clear() { mCheckerList.Clear(); }
private:
nsTArray<mozilla::function<CheckResult()>> mCheckerList;
nsTArray<std::function<CheckResult()>> mCheckerList;
}; // SupportChecker
PDMFactory::PDMFactory()

View File

@ -8,7 +8,6 @@
#define PDMFactory_h_
#include "PlatformDecoderModule.h"
#include "mozilla/Function.h"
#include "mozilla/StaticMutex.h"
class CDMProxy;

View File

@ -7,7 +7,6 @@
#include "mozilla/dom/ContentParent.h"
#include "mozilla/dom/HTMLIFrameElementBinding.h"
#include "mozilla/dom/TabParent.h"
#include "mozilla/Function.h"
#include "mozilla/Logging.h"
#include "mozilla/Move.h"
#include "mozilla/Preferences.h"

View File

@ -441,7 +441,11 @@ QuotaManagerService::PerformIdleMaintenance()
if (!QuotaManager::kRunningXPCShellTests)
#endif
{
// In order to give the correct battery level, hal must have registered
// battery observers.
RegisterBatteryObserver(this);
GetCurrentBatteryInformation(&batteryInfo);
UnregisterBatteryObserver(this);
}
// If we're running XPCShell because we always want to be able to test this
@ -707,6 +711,13 @@ QuotaManagerService::Observe(nsISupports* aSubject,
return NS_OK;
}
void
QuotaManagerService::Notify(const hal::BatteryInformation& aBatteryInfo)
{
// This notification is received when battery data changes. We don't need to
// deal with this notification.
}
NS_IMETHODIMP
AbortOperationsRunnable::Run()
{

View File

@ -8,6 +8,8 @@
#define mozilla_dom_quota_QuotaManagerService_h
#include "mozilla/dom/ipc/IdType.h"
#include "mozilla/dom/battery/Types.h"
#include "mozilla/Observer.h"
#include "nsAutoPtr.h"
#include "nsIObserver.h"
#include "nsIQuotaManagerService.h"
@ -22,6 +24,10 @@ class PBackgroundChild;
} // namespace ipc
namespace hal {
class BatteryInformation;
}
namespace dom {
namespace quota {
@ -31,6 +37,7 @@ class QuotaManager;
class QuotaManagerService final
: public nsIQuotaManagerService
, public nsIObserver
, public BatteryObserver
{
typedef mozilla::ipc::PBackgroundChild PBackgroundChild;
@ -104,6 +111,10 @@ private:
NS_DECL_ISUPPORTS
NS_DECL_NSIQUOTAMANAGERSERVICE
NS_DECL_NSIOBSERVER
// BatteryObserver override
void
Notify(const hal::BatteryInformation& aBatteryInfo) override;
};
} // namespace quota

View File

@ -0,0 +1,15 @@
<!DOCTYPE HTML>
<html>
<head>
<title>Bug 1316826 - 'strict-dynamic' blocking DOM event handlers</title>
</head>
<body>
<div id="testdiv">blocked</div>
<a id="jslink" href='javascript:document.getElementById("testdiv").innerHTML = "allowed"'>click me</a>
<script nonce="foo">
document.getElementById("jslink").click();
</script>
</body>
</html>

View File

@ -189,6 +189,7 @@ support-files =
file_upgrade_insecure_docwrite_iframe.sjs
file_data-uri_blocked.html
file_data-uri_blocked.html^headers^
file_strict_dynamic_js_url.html
file_strict_dynamic_script_events.html
file_strict_dynamic_script_events_xbl.html
file_strict_dynamic_script_inline.html

View File

@ -84,7 +84,13 @@ var tests = [
result: "blocked",
file: "file_strict_dynamic_script_events_xbl.html",
policy: "script-src 'strict-dynamic' 'nonce-foo'"
}
},
{
desc: "strict-dynamic with JS URLs should be blocked",
result: "blocked",
file: "file_strict_dynamic_js_url.html",
policy: "script-src 'strict-dynamic' 'nonce-foo'"
},
];
var counter = 0;

View File

@ -272,10 +272,7 @@ function SetupPrefTestEnvironment(which, additional_prefs) {
["security.mixed_content.use_hsts",
settings.use_hsts],
["security.mixed_content.send_hsts_priming",
settings.send_hsts_priming],
["security.mixed_content.hsts_priming_request_timeout",
30000],
];
settings.send_hsts_priming]];
if (additional_prefs) {
for (let idx in additional_prefs) {

View File

@ -615,9 +615,9 @@ var interfaceNamesInGlobalScope =
// IMPORTANT: Do not change this list without review from a DOM peer!
"InstallTrigger",
// IMPORTANT: Do not change this list without review from a DOM peer!
"IntersectionObserver",
{name: "IntersectionObserver", disabled: true},
// IMPORTANT: Do not change this list without review from a DOM peer!
"IntersectionObserverEntry",
{name: "IntersectionObserverEntry", disabled: true},
// IMPORTANT: Do not change this list without review from a DOM peer!
"KeyEvent",
// IMPORTANT: Do not change this list without review from a DOM peer!

View File

@ -7,7 +7,7 @@
* https://wicg.github.io/IntersectionObserver/
*/
[ProbablyShortLivingObject]
[ProbablyShortLivingObject, Pref="dom.IntersectionObserver.enabled"]
interface IntersectionObserverEntry {
[Constant]
readonly attribute DOMHighResTimeStamp time;
@ -24,7 +24,8 @@ interface IntersectionObserverEntry {
};
[Constructor(IntersectionCallback intersectionCallback,
optional IntersectionObserverInit options)]
optional IntersectionObserverInit options),
Pref="dom.IntersectionObserver.enabled"]
interface IntersectionObserver {
[Constant]
readonly attribute Element? root;

View File

@ -796,6 +796,43 @@ interface WEBGL_compressed_texture_s3tc
const GLenum COMPRESSED_RGBA_S3TC_DXT5_EXT = 0x83F3;
};
[NoInterfaceObject]
interface WEBGL_compressed_texture_astc {
/* Compressed Texture Format */
const GLenum COMPRESSED_RGBA_ASTC_4x4_KHR = 0x93B0;
const GLenum COMPRESSED_RGBA_ASTC_5x4_KHR = 0x93B1;
const GLenum COMPRESSED_RGBA_ASTC_5x5_KHR = 0x93B2;
const GLenum COMPRESSED_RGBA_ASTC_6x5_KHR = 0x93B3;
const GLenum COMPRESSED_RGBA_ASTC_6x6_KHR = 0x93B4;
const GLenum COMPRESSED_RGBA_ASTC_8x5_KHR = 0x93B5;
const GLenum COMPRESSED_RGBA_ASTC_8x6_KHR = 0x93B6;
const GLenum COMPRESSED_RGBA_ASTC_8x8_KHR = 0x93B7;
const GLenum COMPRESSED_RGBA_ASTC_10x5_KHR = 0x93B8;
const GLenum COMPRESSED_RGBA_ASTC_10x6_KHR = 0x93B9;
const GLenum COMPRESSED_RGBA_ASTC_10x8_KHR = 0x93BA;
const GLenum COMPRESSED_RGBA_ASTC_10x10_KHR = 0x93BB;
const GLenum COMPRESSED_RGBA_ASTC_12x10_KHR = 0x93BC;
const GLenum COMPRESSED_RGBA_ASTC_12x12_KHR = 0x93BD;
const GLenum COMPRESSED_SRGB8_ALPHA8_ASTC_4x4_KHR = 0x93D0;
const GLenum COMPRESSED_SRGB8_ALPHA8_ASTC_5x4_KHR = 0x93D1;
const GLenum COMPRESSED_SRGB8_ALPHA8_ASTC_5x5_KHR = 0x93D2;
const GLenum COMPRESSED_SRGB8_ALPHA8_ASTC_6x5_KHR = 0x93D3;
const GLenum COMPRESSED_SRGB8_ALPHA8_ASTC_6x6_KHR = 0x93D4;
const GLenum COMPRESSED_SRGB8_ALPHA8_ASTC_8x5_KHR = 0x93D5;
const GLenum COMPRESSED_SRGB8_ALPHA8_ASTC_8x6_KHR = 0x93D6;
const GLenum COMPRESSED_SRGB8_ALPHA8_ASTC_8x8_KHR = 0x93D7;
const GLenum COMPRESSED_SRGB8_ALPHA8_ASTC_10x5_KHR = 0x93D8;
const GLenum COMPRESSED_SRGB8_ALPHA8_ASTC_10x6_KHR = 0x93D9;
const GLenum COMPRESSED_SRGB8_ALPHA8_ASTC_10x8_KHR = 0x93DA;
const GLenum COMPRESSED_SRGB8_ALPHA8_ASTC_10x10_KHR = 0x93DB;
const GLenum COMPRESSED_SRGB8_ALPHA8_ASTC_12x10_KHR = 0x93DC;
const GLenum COMPRESSED_SRGB8_ALPHA8_ASTC_12x12_KHR = 0x93DD;
// Profile query support.
sequence<DOMString>? getSupportedProfiles();
};
[NoInterfaceObject]
interface WEBGL_compressed_texture_atc
{

View File

@ -4,7 +4,7 @@
# License, v. 2.0. If a copy of the MPL was not distributed with this
# file, You can obtain one at http://mozilla.org/MPL/2.0/.
UNIFIED_SOURCES += [
SOURCES += [
'mozHunspell.cpp',
'mozHunspellDirProvider.cpp',
'RemoteSpellCheckEngineChild.cpp',

View File

@ -200,7 +200,7 @@ NS_IMETHODIMP mozHunspell::SetDictionary(const char16_t *aDictionary)
if (!mHunspell)
return NS_ERROR_OUT_OF_MEMORY;
nsAutoCString label(mHunspell->get_dict_encoding().c_str());
nsDependentCString label(mHunspell->get_dic_encoding());
nsAutoCString encoding;
if (!EncodingUtils::FindEncodingForLabelNoReplacement(label, encoding)) {
return NS_ERROR_UCONV_NOCONV;
@ -480,8 +480,7 @@ mozHunspell::LoadDictionariesFromDir(nsIFile* aDir)
return NS_OK;
}
nsresult
mozHunspell::ConvertCharset(const char16_t* aStr, std::string* aDst)
nsresult mozHunspell::ConvertCharset(const char16_t* aStr, char ** aDst)
{
NS_ENSURE_ARG_POINTER(aDst);
NS_ENSURE_TRUE(mEncoder, NS_ERROR_NULL_POINTER);
@ -491,13 +490,12 @@ mozHunspell::ConvertCharset(const char16_t* aStr, std::string* aDst)
nsresult rv = mEncoder->GetMaxLength(aStr, inLength, &outLength);
NS_ENSURE_SUCCESS(rv, rv);
aDst->resize(outLength);
*aDst = (char *) moz_xmalloc(sizeof(char) * (outLength+1));
NS_ENSURE_TRUE(*aDst, NS_ERROR_OUT_OF_MEMORY);
char* dst = &aDst->operator[](0);
rv = mEncoder->Convert(aStr, &inLength, dst, &outLength);
if (NS_SUCCEEDED(rv)) {
aDst->resize(outLength);
}
rv = mEncoder->Convert(aStr, &inLength, *aDst, &outLength);
if (NS_SUCCEEDED(rv))
(*aDst)[outLength] = '\0';
return rv;
}
@ -520,11 +518,12 @@ NS_IMETHODIMP mozHunspell::Check(const char16_t *aWord, bool *aResult)
NS_ENSURE_ARG_POINTER(aResult);
NS_ENSURE_TRUE(mHunspell, NS_ERROR_FAILURE);
std::string charsetWord;
nsresult rv = ConvertCharset(aWord, &charsetWord);
nsXPIDLCString charsetWord;
nsresult rv = ConvertCharset(aWord, getter_Copies(charsetWord));
NS_ENSURE_SUCCESS(rv, rv);
*aResult = mHunspell->spell(charsetWord);
*aResult = !!mHunspell->spell(charsetWord);
if (!*aResult && mPersonalDictionary)
rv = mPersonalDictionary->Check(aWord, mLanguage.get(), aResult);
@ -541,12 +540,12 @@ NS_IMETHODIMP mozHunspell::Suggest(const char16_t *aWord, char16_t ***aSuggestio
nsresult rv;
*aSuggestionCount = 0;
std::string charsetWord;
rv = ConvertCharset(aWord, &charsetWord);
nsXPIDLCString charsetWord;
rv = ConvertCharset(aWord, getter_Copies(charsetWord));
NS_ENSURE_SUCCESS(rv, rv);
std::vector<std::string> suggestions = mHunspell->suggest(charsetWord);
*aSuggestionCount = static_cast<uint32_t>(suggestions.size());
char ** wlst;
*aSuggestionCount = mHunspell->suggest(&wlst, charsetWord);
if (*aSuggestionCount) {
*aSuggestions = (char16_t **)moz_xmalloc(*aSuggestionCount * sizeof(char16_t *));
@ -554,15 +553,15 @@ NS_IMETHODIMP mozHunspell::Suggest(const char16_t *aWord, char16_t ***aSuggestio
uint32_t index = 0;
for (index = 0; index < *aSuggestionCount && NS_SUCCEEDED(rv); ++index) {
// Convert the suggestion to utf16
int32_t inLength = suggestions[index].size();
int32_t inLength = strlen(wlst[index]);
int32_t outLength;
rv = mDecoder->GetMaxLength(suggestions[index].c_str(), inLength, &outLength);
rv = mDecoder->GetMaxLength(wlst[index], inLength, &outLength);
if (NS_SUCCEEDED(rv))
{
(*aSuggestions)[index] = (char16_t *) moz_xmalloc(sizeof(char16_t) * (outLength+1));
if ((*aSuggestions)[index])
{
rv = mDecoder->Convert(suggestions[index].c_str(), &inLength, (*aSuggestions)[index], &outLength);
rv = mDecoder->Convert(wlst[index], &inLength, (*aSuggestions)[index], &outLength);
if (NS_SUCCEEDED(rv))
(*aSuggestions)[index][outLength] = 0;
}
@ -578,6 +577,7 @@ NS_IMETHODIMP mozHunspell::Suggest(const char16_t *aWord, char16_t ***aSuggestio
rv = NS_ERROR_OUT_OF_MEMORY;
}
NS_FREE_XPCOM_ALLOCATED_POINTER_ARRAY(*aSuggestionCount, wlst);
return rv;
}

View File

@ -99,7 +99,7 @@ public:
void LoadDictionaryList(bool aNotifyChildProcesses);
// helper method for converting a word to the charset of the dictionary
nsresult ConvertCharset(const char16_t* aStr, std::string* aDst);
nsresult ConvertCharset(const char16_t* aStr, char ** aDst);
NS_DECL_NSIMEMORYREPORTER

View File

@ -1,2 +1,2 @@
Hunspell Version: 1.5.0
Hunspell Version: 1.4.1
Additional Patches: See patches directory.

View File

@ -79,7 +79,33 @@
#include "affentry.hxx"
#include "csutil.hxx"
AffEntry::~AffEntry() {
PfxEntry::PfxEntry(AffixMgr* pmgr, affentry* dp)
// register affix manager
: pmyMgr(pmgr),
next(NULL),
nexteq(NULL),
nextne(NULL),
flgnxt(NULL) {
// set up its initial values
aflag = dp->aflag; // flag
strip = dp->strip; // string to strip
appnd = dp->appnd; // string to append
numconds = dp->numconds; // length of the condition
opts = dp->opts; // cross product flag
// then copy over all of the conditions
if (opts & aeLONGCOND) {
memcpy(c.conds, dp->c.l.conds1, MAXCONDLEN_1);
c.l.conds2 = dp->c.l.conds2;
} else
memcpy(c.conds, dp->c.conds, MAXCONDLEN);
morphcode = dp->morphcode;
contclass = dp->contclass;
contclasslen = dp->contclasslen;
}
PfxEntry::~PfxEntry() {
aflag = 0;
pmyMgr = NULL;
if (opts & aeLONGCOND)
free(c.l.conds2);
if (morphcode && !(opts & aeALIASM))
@ -88,26 +114,17 @@ AffEntry::~AffEntry() {
free(contclass);
}
PfxEntry::PfxEntry(AffixMgr* pmgr)
// register affix manager
: pmyMgr(pmgr),
next(NULL),
nexteq(NULL),
nextne(NULL),
flgnxt(NULL) {
}
// add prefix to this word assuming conditions hold
std::string PfxEntry::add(const char* word, size_t len) {
std::string result;
char* PfxEntry::add(const char* word, size_t len) {
if ((len > strip.size() || (len == 0 && pmyMgr->get_fullstrip())) &&
(len >= numconds) && test_condition(word) &&
(!strip.size() || (strncmp(word, strip.c_str(), strip.size()) == 0))) {
/* we have a match so add prefix */
result.assign(appnd);
result.append(word + strip.size());
std::string tword(appnd);
tword.append(word + strip.size());
return mystrdup(tword.c_str());
}
return result;
return NULL;
}
inline char* PfxEntry::nextchar(char* p) {
@ -259,7 +276,8 @@ struct hentry* PfxEntry::checkword(const char* word,
// if ((opts & aeXPRODUCT) && in_compound) {
if ((opts & aeXPRODUCT)) {
he = pmyMgr->suffix_check(tmpword.c_str(), tmpl, aeXPRODUCT, this,
FLAG_NULL, needflag, in_compound);
NULL, 0, NULL, FLAG_NULL, needflag,
in_compound);
if (he)
return he;
}
@ -273,6 +291,8 @@ struct hentry* PfxEntry::check_twosfx(const char* word,
int len,
char in_compound,
const FLAG needflag) {
struct hentry* he; // hash entry of root word or NULL
// on entry prefix is 0 length or already matches the beginning of the word.
// So if the remaining root word has positive length
// and if there are enough chars in root word and added back strip chars
@ -304,9 +324,8 @@ struct hentry* PfxEntry::check_twosfx(const char* word,
// cross checked combined with a suffix
if ((opts & aeXPRODUCT) && (in_compound != IN_CPD_BEGIN)) {
// hash entry of root word or NULL
struct hentry* he = pmyMgr->suffix_check_twosfx(tmpword.c_str(), tmpl, aeXPRODUCT, this,
needflag);
he = pmyMgr->suffix_check_twosfx(tmpword.c_str(), tmpl, aeXPRODUCT, this,
needflag);
if (he)
return he;
}
@ -316,15 +335,15 @@ struct hentry* PfxEntry::check_twosfx(const char* word,
}
// check if this prefix entry matches
std::string PfxEntry::check_twosfx_morph(const char* word,
int len,
char in_compound,
const FLAG needflag) {
std::string result;
char* PfxEntry::check_twosfx_morph(const char* word,
int len,
char in_compound,
const FLAG needflag) {
// on entry prefix is 0 length or already matches the beginning of the word.
// So if the remaining root word has positive length
// and if there are enough chars in root word and added back strip chars
// to meet the number of characters conditions, then test it
int tmpl = len - appnd.size(); // length of tmpword
if ((tmpl > 0 || (tmpl == 0 && pmyMgr->get_fullstrip())) &&
@ -351,21 +370,22 @@ std::string PfxEntry::check_twosfx_morph(const char* word,
// ross checked combined with a suffix
if ((opts & aeXPRODUCT) && (in_compound != IN_CPD_BEGIN)) {
result = pmyMgr->suffix_check_twosfx_morph(tmpword.c_str(), tmpl,
aeXPRODUCT,
this, needflag);
return pmyMgr->suffix_check_twosfx_morph(tmpword.c_str(), tmpl,
aeXPRODUCT,
this, needflag);
}
}
}
return result;
return NULL;
}
// check if this prefix entry matches
std::string PfxEntry::check_morph(const char* word,
int len,
char in_compound,
const FLAG needflag) {
std::string result;
char* PfxEntry::check_morph(const char* word,
int len,
char in_compound,
const FLAG needflag) {
struct hentry* he; // hash entry of root word or NULL
char* st;
// on entry prefix is 0 length or already matches the beginning of the word.
// So if the remaining root word has positive length
@ -391,8 +411,9 @@ std::string PfxEntry::check_morph(const char* word,
// root word in the dictionary
if (test_condition(tmpword.c_str())) {
std::string result;
tmpl += strip.size();
struct hentry* he; // hash entry of root word or NULL
if ((he = pmyMgr->lookup(tmpword.c_str())) != NULL) {
do {
if (TESTAFF(he->astr, aflag, he->alen) &&
@ -434,19 +455,23 @@ std::string PfxEntry::check_morph(const char* word,
// ross checked combined with a suffix
if ((opts & aeXPRODUCT) && (in_compound != IN_CPD_BEGIN)) {
std::string st = pmyMgr->suffix_check_morph(tmpword.c_str(), tmpl, aeXPRODUCT, this,
FLAG_NULL, needflag);
if (!st.empty()) {
st = pmyMgr->suffix_check_morph(tmpword.c_str(), tmpl, aeXPRODUCT, this,
FLAG_NULL, needflag);
if (st) {
result.append(st);
free(st);
}
}
if (!result.empty())
return mystrdup(result.c_str());
}
}
return result;
return NULL;
}
SfxEntry::SfxEntry(AffixMgr* pmgr)
SfxEntry::SfxEntry(AffixMgr* pmgr, affentry* dp)
: pmyMgr(pmgr) // register affix manager
,
next(NULL),
@ -456,21 +481,50 @@ SfxEntry::SfxEntry(AffixMgr* pmgr)
l_morph(NULL),
r_morph(NULL),
eq_morph(NULL) {
// set up its initial values
aflag = dp->aflag; // char flag
strip = dp->strip; // string to strip
appnd = dp->appnd; // string to append
numconds = dp->numconds; // length of the condition
opts = dp->opts; // cross product flag
// then copy over all of the conditions
if (opts & aeLONGCOND) {
memcpy(c.l.conds1, dp->c.l.conds1, MAXCONDLEN_1);
c.l.conds2 = dp->c.l.conds2;
} else
memcpy(c.conds, dp->c.conds, MAXCONDLEN);
rappnd = appnd;
reverseword(rappnd);
morphcode = dp->morphcode;
contclass = dp->contclass;
contclasslen = dp->contclasslen;
}
SfxEntry::~SfxEntry() {
aflag = 0;
pmyMgr = NULL;
if (opts & aeLONGCOND)
free(c.l.conds2);
if (morphcode && !(opts & aeALIASM))
free(morphcode);
if (contclass && !(opts & aeALIASF))
free(contclass);
}
// add suffix to this word assuming conditions hold
std::string SfxEntry::add(const char* word, size_t len) {
std::string result;
char* SfxEntry::add(const char* word, size_t len) {
/* make sure all conditions match */
if ((len > strip.size() || (len == 0 && pmyMgr->get_fullstrip())) &&
(len >= numconds) && test_condition(word + len, word) &&
(!strip.size() ||
(strcmp(word + len - strip.size(), strip.c_str()) == 0))) {
result.assign(word);
std::string tword(word);
/* we have a match so add suffix */
result.replace(len - strip.size(), std::string::npos, appnd);
tword.replace(len - strip.size(), std::string::npos, appnd);
return mystrdup(tword.c_str());
}
return result;
return NULL;
}
inline char* SfxEntry::nextchar(char* p) {
@ -615,6 +669,9 @@ struct hentry* SfxEntry::checkword(const char* word,
int len,
int optflags,
PfxEntry* ppfx,
char** wlst,
int maxSug,
int* ns,
const FLAG cclass,
const FLAG needflag,
const FLAG badflag) {
@ -685,6 +742,27 @@ struct hentry* SfxEntry::checkword(const char* word,
return he;
he = he->next_homonym; // check homonyms
} while (he);
// obsolote stemming code (used only by the
// experimental SuffixMgr:suggest_pos_stems)
// store resulting root in wlst
} else if (wlst && (*ns < maxSug)) {
int cwrd = 1;
for (int k = 0; k < *ns; k++)
if (strcmp(tmpword, wlst[k]) == 0) {
cwrd = 0;
break;
}
if (cwrd) {
wlst[*ns] = mystrdup(tmpword);
if (wlst[*ns] == NULL) {
for (int j = 0; j < *ns; j++)
free(wlst[j]);
*ns = -1;
return NULL;
}
(*ns)++;
}
}
}
}
@ -697,6 +775,7 @@ struct hentry* SfxEntry::check_twosfx(const char* word,
int optflags,
PfxEntry* ppfx,
const FLAG needflag) {
struct hentry* he; // hash entry pointer
PfxEntry* ep = ppfx;
// if this suffix is being cross checked with a prefix
@ -734,18 +813,17 @@ struct hentry* SfxEntry::check_twosfx(const char* word,
// if all conditions are met then recall suffix_check
if (test_condition(end, beg)) {
struct hentry* he; // hash entry pointer
if (ppfx) {
// handle conditional suffix
if ((contclass) && TESTAFF(contclass, ep->getFlag(), contclasslen))
he = pmyMgr->suffix_check(tmpword.c_str(), tmpl, 0, NULL,
(FLAG)aflag, needflag, IN_CPD_NOT);
he = pmyMgr->suffix_check(tmpword.c_str(), tmpl, 0, NULL, NULL, 0, NULL,
(FLAG)aflag, needflag);
else
he = pmyMgr->suffix_check(tmpword.c_str(), tmpl, optflags, ppfx,
(FLAG)aflag, needflag, IN_CPD_NOT);
he = pmyMgr->suffix_check(tmpword.c_str(), tmpl, optflags, ppfx, NULL, 0,
NULL, (FLAG)aflag, needflag);
} else {
he = pmyMgr->suffix_check(tmpword.c_str(), tmpl, 0, NULL,
(FLAG)aflag, needflag, IN_CPD_NOT);
he = pmyMgr->suffix_check(tmpword.c_str(), tmpl, 0, NULL, NULL, 0, NULL,
(FLAG)aflag, needflag);
}
if (he)
return he;
@ -755,20 +833,23 @@ struct hentry* SfxEntry::check_twosfx(const char* word,
}
// see if two-level suffix is present in the word
std::string SfxEntry::check_twosfx_morph(const char* word,
int len,
int optflags,
PfxEntry* ppfx,
const FLAG needflag) {
char* SfxEntry::check_twosfx_morph(const char* word,
int len,
int optflags,
PfxEntry* ppfx,
const FLAG needflag) {
PfxEntry* ep = ppfx;
char* st;
std::string result;
char result[MAXLNLEN];
*result = '\0';
// if this suffix is being cross checked with a prefix
// but it does not support cross products skip it
if ((optflags & aeXPRODUCT) != 0 && (opts & aeXPRODUCT) == 0)
return result;
return NULL;
// upon entry suffix is 0 length or already matches the end of the word.
// So if the remaining root word has positive length
@ -802,34 +883,40 @@ std::string SfxEntry::check_twosfx_morph(const char* word,
if (ppfx) {
// handle conditional suffix
if ((contclass) && TESTAFF(contclass, ep->getFlag(), contclasslen)) {
std::string st = pmyMgr->suffix_check_morph(tmpword.c_str(), tmpl, 0, NULL, aflag,
needflag);
if (!st.empty()) {
st = pmyMgr->suffix_check_morph(tmpword.c_str(), tmpl, 0, NULL, aflag,
needflag);
if (st) {
if (ppfx->getMorph()) {
result.append(ppfx->getMorph());
result.append(" ");
mystrcat(result, ppfx->getMorph(), MAXLNLEN);
mystrcat(result, " ", MAXLNLEN);
}
result.append(st);
mystrcat(result, st, MAXLNLEN);
free(st);
mychomp(result);
}
} else {
std::string st = pmyMgr->suffix_check_morph(tmpword.c_str(), tmpl, optflags, ppfx, aflag,
needflag);
if (!st.empty()) {
result.append(st);
st = pmyMgr->suffix_check_morph(tmpword.c_str(), tmpl, optflags, ppfx, aflag,
needflag);
if (st) {
mystrcat(result, st, MAXLNLEN);
free(st);
mychomp(result);
}
}
} else {
std::string st = pmyMgr->suffix_check_morph(tmpword.c_str(), tmpl, 0, NULL, aflag, needflag);
if (!st.empty()) {
result.append(st);
st =
pmyMgr->suffix_check_morph(tmpword.c_str(), tmpl, 0, NULL, aflag, needflag);
if (st) {
mystrcat(result, st, MAXLNLEN);
free(st);
mychomp(result);
}
}
if (*result)
return mystrdup(result);
}
}
return result;
return NULL;
}
// get next homonym with same affix
@ -861,11 +948,6 @@ struct hentry* SfxEntry::get_next_homonym(struct hentry* he,
return NULL;
}
void SfxEntry::initReverseWord() {
rappnd = appnd;
reverseword(rappnd);
}
#if 0
Appendix: Understanding Affix Code

View File

@ -71,8 +71,10 @@
* SUCH DAMAGE.
*/
#ifndef AFFIX_HXX_
#define AFFIX_HXX_
#ifndef _AFFIX_HXX_
#define _AFFIX_HXX_
#include "hunvisapi.h"
#include "atypes.hxx"
#include "baseaffix.hxx"
@ -80,7 +82,7 @@
/* A Prefix Entry */
class PfxEntry : public AffEntry {
class LIBHUNSPELL_DLL_EXPORTED PfxEntry : protected AffEntry {
private:
PfxEntry(const PfxEntry&);
PfxEntry& operator=(const PfxEntry&);
@ -94,9 +96,10 @@ class PfxEntry : public AffEntry {
PfxEntry* flgnxt;
public:
explicit PfxEntry(AffixMgr* pmgr);
PfxEntry(AffixMgr* pmgr, affentry* dp);
~PfxEntry();
bool allowCross() const { return ((opts & aeXPRODUCT) != 0); }
inline bool allowCross() { return ((opts & aeXPRODUCT) != 0); }
struct hentry* checkword(const char* word,
int len,
char in_compound,
@ -107,19 +110,19 @@ class PfxEntry : public AffEntry {
char in_compound,
const FLAG needflag = FLAG_NULL);
std::string check_morph(const char* word,
int len,
char in_compound,
const FLAG needflag = FLAG_NULL);
char* check_morph(const char* word,
int len,
char in_compound,
const FLAG needflag = FLAG_NULL);
std::string check_twosfx_morph(const char* word,
int len,
char in_compound,
const FLAG needflag = FLAG_NULL);
char* check_twosfx_morph(const char* word,
int len,
char in_compound,
const FLAG needflag = FLAG_NULL);
FLAG getFlag() { return aflag; }
const char* getKey() { return appnd.c_str(); }
std::string add(const char* word, size_t len);
inline FLAG getFlag() { return aflag; }
inline const char* getKey() { return appnd.c_str(); }
char* add(const char* word, size_t len);
inline short getKeyLen() { return appnd.size(); }
@ -144,7 +147,7 @@ class PfxEntry : public AffEntry {
/* A Suffix Entry */
class SfxEntry : public AffEntry {
class LIBHUNSPELL_DLL_EXPORTED SfxEntry : protected AffEntry {
private:
SfxEntry(const SfxEntry&);
SfxEntry& operator=(const SfxEntry&);
@ -163,16 +166,20 @@ class SfxEntry : public AffEntry {
SfxEntry* eq_morph;
public:
explicit SfxEntry(AffixMgr* pmgr);
SfxEntry(AffixMgr* pmgr, affentry* dp);
~SfxEntry();
bool allowCross() const { return ((opts & aeXPRODUCT) != 0); }
inline bool allowCross() { return ((opts & aeXPRODUCT) != 0); }
struct hentry* checkword(const char* word,
int len,
int optflags,
PfxEntry* ppfx,
const FLAG cclass,
const FLAG needflag,
const FLAG badflag);
char** wlst,
int maxSug,
int* ns,
const FLAG cclass = FLAG_NULL,
const FLAG needflag = FLAG_NULL,
const FLAG badflag = FLAG_NULL);
struct hentry* check_twosfx(const char* word,
int len,
@ -180,11 +187,11 @@ class SfxEntry : public AffEntry {
PfxEntry* ppfx,
const FLAG needflag = FLAG_NULL);
std::string check_twosfx_morph(const char* word,
int len,
int optflags,
PfxEntry* ppfx,
const FLAG needflag = FLAG_NULL);
char* check_twosfx_morph(const char* word,
int len,
int optflags,
PfxEntry* ppfx,
const FLAG needflag = FLAG_NULL);
struct hentry* get_next_homonym(struct hentry* he);
struct hentry* get_next_homonym(struct hentry* word,
int optflags,
@ -192,9 +199,9 @@ class SfxEntry : public AffEntry {
const FLAG cclass,
const FLAG needflag);
FLAG getFlag() { return aflag; }
const char* getKey() { return rappnd.c_str(); }
std::string add(const char* word, size_t len);
inline FLAG getFlag() { return aflag; }
inline const char* getKey() { return rappnd.c_str(); }
char* add(const char* word, size_t len);
inline const char* getMorph() { return morphcode; }
@ -217,7 +224,6 @@ class SfxEntry : public AffEntry {
inline void setNextNE(SfxEntry* ptr) { nextne = ptr; }
inline void setNextEQ(SfxEntry* ptr) { nexteq = ptr; }
inline void setFlgNxt(SfxEntry* ptr) { flgnxt = ptr; }
void initReverseWord();
inline char* nextchar(char* p);
inline int test_condition(const char* st, const char* begin);

File diff suppressed because it is too large Load Diff

View File

@ -71,13 +71,14 @@
* SUCH DAMAGE.
*/
#ifndef AFFIXMGR_HXX_
#define AFFIXMGR_HXX_
#ifndef _AFFIXMGR_HXX_
#define _AFFIXMGR_HXX_
#include "hunvisapi.h"
#include <stdio.h>
#include <string>
#include <vector>
#include "atypes.hxx"
#include "baseaffix.hxx"
@ -92,16 +93,17 @@
class PfxEntry;
class SfxEntry;
class AffixMgr {
class LIBHUNSPELL_DLL_EXPORTED AffixMgr {
PfxEntry* pStart[SETSIZE];
SfxEntry* sStart[SETSIZE];
PfxEntry* pFlag[SETSIZE];
SfxEntry* sFlag[SETSIZE];
const std::vector<HashMgr*>& alldic;
const HashMgr* pHMgr;
std::string keystring;
std::string trystring;
std::string encoding;
HashMgr* pHMgr;
HashMgr** alldic;
int* maxdic;
char* keystring;
char* trystring;
char* encoding;
struct cs_info* csconv;
int utf8;
int complexprefixes;
@ -123,19 +125,19 @@ class AffixMgr {
FLAG nongramsuggest;
FLAG needaffix;
int cpdmin;
bool parsedrep;
std::vector<replentry> reptable;
int numrep;
replentry* reptable;
RepList* iconvtable;
RepList* oconvtable;
bool parsedmaptable;
std::vector<mapentry> maptable;
bool parsedbreaktable;
std::vector<std::string> breaktable;
bool parsedcheckcpd;
std::vector<patentry> checkcpdtable;
int nummap;
mapentry* maptable;
int numbreak;
char** breaktable;
int numcheckcpd;
patentry* checkcpdtable;
int simplifiedcpd;
bool parseddefcpd;
std::vector<flagentry> defcpdtable;
int numdefcpd;
flagentry* defcpdtable;
phonetable* phone;
int maxngramsugs;
int maxcpdsugs;
@ -145,9 +147,10 @@ class AffixMgr {
int sugswithdots;
int cpdwordmax;
int cpdmaxsyllable;
std::string cpdvowels; // vowels (for calculating of Hungarian compounding limit,
std::vector<w_char> cpdvowels_utf16; //vowels for UTF-8 encoding
std::string cpdsyllablenum; // syllable count incrementing flag
char* cpdvowels;
w_char* cpdvowels_utf16;
int cpdvowels_utf16_len;
char* cpdsyllablenum;
const char* pfxappnd; // BUG: not stateless
const char* sfxappnd; // BUG: not stateless
int sfxextra; // BUG: not stateless
@ -156,12 +159,12 @@ class AffixMgr {
SfxEntry* sfx; // BUG: not stateless
PfxEntry* pfx; // BUG: not stateless
int checknum;
std::string wordchars; // letters + spec. word characters
char* wordchars;
std::vector<w_char> wordchars_utf16;
std::string ignorechars; // letters + spec. word characters
char* ignorechars;
std::vector<w_char> ignorechars_utf16;
std::string version; // affix and dictionary file version string
std::string lang; // language
char* version;
char* lang;
int langnum;
FLAG lemma_present;
FLAG circumfix;
@ -179,7 +182,7 @@ class AffixMgr {
// affix)
public:
AffixMgr(const char* affpath, const std::vector<HashMgr*>& ptr, const char* key = NULL);
AffixMgr(const char* affpath, HashMgr** ptr, int* md, const char* key = NULL);
~AffixMgr();
struct hentry* affix_check(const char* word,
int len,
@ -199,6 +202,9 @@ class AffixMgr {
int len,
int sfxopts,
PfxEntry* ppfx,
char** wlst,
int maxSug,
int* ns,
const FLAG cclass = FLAG_NULL,
const FLAG needflag = FLAG_NULL,
char in_compound = IN_CPD_NOT);
@ -208,39 +214,39 @@ class AffixMgr {
PfxEntry* ppfx,
const FLAG needflag = FLAG_NULL);
std::string affix_check_morph(const char* word,
int len,
const FLAG needflag = FLAG_NULL,
char in_compound = IN_CPD_NOT);
std::string prefix_check_morph(const char* word,
int len,
char in_compound,
const FLAG needflag = FLAG_NULL);
std::string suffix_check_morph(const char* word,
int len,
int sfxopts,
PfxEntry* ppfx,
const FLAG cclass = FLAG_NULL,
const FLAG needflag = FLAG_NULL,
char in_compound = IN_CPD_NOT);
char* affix_check_morph(const char* word,
int len,
const FLAG needflag = FLAG_NULL,
char in_compound = IN_CPD_NOT);
char* prefix_check_morph(const char* word,
int len,
char in_compound,
const FLAG needflag = FLAG_NULL);
char* suffix_check_morph(const char* word,
int len,
int sfxopts,
PfxEntry* ppfx,
const FLAG cclass = FLAG_NULL,
const FLAG needflag = FLAG_NULL,
char in_compound = IN_CPD_NOT);
std::string prefix_check_twosfx_morph(const char* word,
int len,
char in_compound,
const FLAG needflag = FLAG_NULL);
std::string suffix_check_twosfx_morph(const char* word,
int len,
int sfxopts,
PfxEntry* ppfx,
const FLAG needflag = FLAG_NULL);
char* prefix_check_twosfx_morph(const char* word,
int len,
char in_compound,
const FLAG needflag = FLAG_NULL);
char* suffix_check_twosfx_morph(const char* word,
int len,
int sfxopts,
PfxEntry* ppfx,
const FLAG needflag = FLAG_NULL);
std::string morphgen(const char* ts,
int wl,
const unsigned short* ap,
unsigned short al,
const char* morph,
const char* targetmorph,
int level);
char* morphgen(const char* ts,
int wl,
const unsigned short* ap,
unsigned short al,
const char* morph,
const char* targetmorph,
int level);
int expand_rootword(struct guessword* wlst,
int maxn,
@ -267,7 +273,8 @@ class AffixMgr {
int cpdcase_check(const char* word, int len);
inline int candidate_check(const char* word, int len);
void setcminmax(int* cmin, int* cmax, const char* word, int len);
struct hentry* compound_check(const std::string& word,
struct hentry* compound_check(const char* word,
int len,
short wordnum,
short numsyllable,
short maxwordnum,
@ -287,37 +294,47 @@ class AffixMgr {
hentry** words,
hentry** rwords,
char hu_mov_rule,
std::string& result,
const std::string* partresult);
char** result,
char* partresult);
std::vector<std::string> get_suffix_words(short unsigned* suff,
int get_suffix_words(short unsigned* suff,
int len,
const char* root_word);
const char* root_word,
char** slst);
struct hentry* lookup(const char* word);
const std::vector<replentry>& get_reptable() const;
int get_numrep() const;
struct replentry* get_reptable() const;
RepList* get_iconvtable() const;
RepList* get_oconvtable() const;
struct phonetable* get_phonetable() const;
const std::vector<mapentry>& get_maptable() const;
const std::vector<std::string>& get_breaktable() const;
const std::string& get_encoding();
int get_nummap() const;
struct mapentry* get_maptable() const;
int get_numbreak() const;
char** get_breaktable() const;
char* get_encoding();
int get_langnum() const;
char* get_key_string();
char* get_try_string() const;
const std::string& get_wordchars() const;
const char* get_wordchars() const;
const std::vector<w_char>& get_wordchars_utf16() const;
const char* get_ignore() const;
char* get_ignore() const;
const std::vector<w_char>& get_ignore_utf16() const;
int get_compound() const;
FLAG get_compoundflag() const;
FLAG get_compoundbegin() const;
FLAG get_forbiddenword() const;
FLAG get_nosuggest() const;
FLAG get_nongramsuggest() const;
FLAG get_needaffix() const;
FLAG get_onlyincompound() const;
FLAG get_compoundroot() const;
FLAG get_lemma_present() const;
int get_checknum() const;
const char* get_prefix() const;
const char* get_suffix() const;
const char* get_derived() const;
const std::string& get_version() const;
const char* get_version() const;
int have_contclass() const;
int get_utf8() const;
int get_complexprefixes() const;
@ -338,25 +355,26 @@ class AffixMgr {
private:
int parse_file(const char* affpath, const char* key);
bool parse_flag(const std::string& line, unsigned short* out, FileMgr* af);
bool parse_num(const std::string& line, int* out, FileMgr* af);
bool parse_cpdsyllable(const std::string& line, FileMgr* af);
bool parse_reptable(const std::string& line, FileMgr* af);
bool parse_convtable(const std::string& line,
int parse_flag(char* line, unsigned short* out, FileMgr* af);
int parse_num(char* line, int* out, FileMgr* af);
int parse_cpdsyllable(char* line, FileMgr* af);
int parse_reptable(char* line, FileMgr* af);
int parse_convtable(char* line,
FileMgr* af,
RepList** rl,
const std::string& keyword);
bool parse_phonetable(const std::string& line, FileMgr* af);
bool parse_maptable(const std::string& line, FileMgr* af);
bool parse_breaktable(const std::string& line, FileMgr* af);
bool parse_checkcpdtable(const std::string& line, FileMgr* af);
bool parse_defcpdtable(const std::string& line, FileMgr* af);
bool parse_affix(const std::string& line, const char at, FileMgr* af, char* dupflags);
const char* keyword);
int parse_phonetable(char* line, FileMgr* af);
int parse_maptable(char* line, FileMgr* af);
int parse_breaktable(char* line, FileMgr* af);
int parse_checkcpdtable(char* line, FileMgr* af);
int parse_defcpdtable(char* line, FileMgr* af);
int parse_affix(char* line, const char at, FileMgr* af, char* dupflags);
void reverse_condition(std::string&);
void debugflag(char* result, unsigned short flag);
std::string& debugflag(std::string& result, unsigned short flag);
int condlen(const char*);
int encodeit(AffEntry& entry, const char* cs);
int encodeit(affentry& entry, const char* cs);
int build_pfxtree(PfxEntry* pfxptr);
int build_sfxtree(SfxEntry* sfxptr);
int process_pfx_order();

View File

@ -38,8 +38,8 @@
*
* ***** END LICENSE BLOCK ***** */
#ifndef ATYPES_HXX_
#define ATYPES_HXX_
#ifndef _ATYPES_HXX_
#define _ATYPES_HXX_
#ifndef HUNSPELL_WARNING
#include <stdio.h>
@ -63,7 +63,7 @@ static inline void HUNSPELL_WARNING(FILE*, const char*, ...) {}
#define SETSIZE 256
#define CONTSIZE 65536
// AffEntry options
// affentry options
#define aeXPRODUCT (1 << 0)
#define aeUTF8 (1 << 1)
#define aeALIASF (1 << 2)
@ -85,6 +85,8 @@ static inline void HUNSPELL_WARNING(FILE*, const char*, ...) {}
#define SPELL_ORIGCAP (1 << 5)
#define SPELL_WARN (1 << 6)
#define MAXLNLEN 8192
#define MINCPDLEN 3
#define MAXCOMPOUND 10
#define MAXCONDLEN 20
@ -98,25 +100,46 @@ static inline void HUNSPELL_WARNING(FILE*, const char*, ...) {}
#define TESTAFF(a, b, c) (std::binary_search(a, a + c, b))
struct affentry {
std::string strip;
std::string appnd;
char numconds;
char opts;
unsigned short aflag;
unsigned short* contclass;
short contclasslen;
union {
char conds[MAXCONDLEN];
struct {
char conds1[MAXCONDLEN_1];
char* conds2;
} l;
} c;
char* morphcode;
};
struct guessword {
char* word;
bool allow;
char* orig;
};
typedef std::vector<std::string> mapentry;
typedef std::vector<FLAG> flagentry;
struct mapentry {
char** set;
int len;
};
struct flagentry {
FLAG* def;
int len;
};
struct patentry {
std::string pattern;
std::string pattern2;
std::string pattern3;
char* pattern;
char* pattern2;
char* pattern3;
FLAG cond;
FLAG cond2;
patentry()
: cond(FLAG_NULL)
, cond2(FLAG_NULL) {
}
};
#endif

View File

@ -38,17 +38,18 @@
*
* ***** END LICENSE BLOCK ***** */
#ifndef BASEAFF_HXX_
#define BASEAFF_HXX_
#ifndef _BASEAFF_HXX_
#define _BASEAFF_HXX_
#include "hunvisapi.h"
#include <string>
class AffEntry {
class LIBHUNSPELL_DLL_EXPORTED AffEntry {
private:
AffEntry(const AffEntry&);
AffEntry& operator=(const AffEntry&);
public:
protected:
AffEntry()
: numconds(0),
opts(0),
@ -56,7 +57,6 @@ class AffEntry {
morphcode(0),
contclass(NULL),
contclasslen(0) {}
virtual ~AffEntry();
std::string appnd;
std::string strip;
unsigned char numconds;

View File

@ -76,7 +76,6 @@
#include <string.h>
#include <stdio.h>
#include <ctype.h>
#include <sstream>
#include "csutil.hxx"
#include "atypes.hxx"
@ -123,24 +122,26 @@ static struct unicode_info2* utf_tbl = NULL;
static int utf_tbl_count =
0; // utf_tbl can be used by multiple Hunspell instances
void myopen(std::ifstream& stream, const char* path, std::ios_base::openmode mode)
{
#if defined(_WIN32) && defined(_MSC_VER)
FILE* myfopen(const char* path, const char* mode) {
#ifdef _WIN32
#define WIN32_LONG_PATH_PREFIX "\\\\?\\"
if (strncmp(path, WIN32_LONG_PATH_PREFIX, 4) == 0) {
int len = MultiByteToWideChar(CP_UTF8, 0, path, -1, NULL, 0);
wchar_t* buff = new wchar_t[len];
wchar_t* buff2 = new wchar_t[len];
MultiByteToWideChar(CP_UTF8, 0, path, -1, buff, len);
if (_wfullpath(buff2, buff, len) != NULL) {
stream.open(buff2, mode);
wchar_t* buff = (wchar_t*)malloc(len * sizeof(wchar_t));
wchar_t* buff2 = (wchar_t*)malloc(len * sizeof(wchar_t));
FILE* f = NULL;
if (buff && buff2) {
MultiByteToWideChar(CP_UTF8, 0, path, -1, buff, len);
if (_wfullpath(buff2, buff, len) != NULL) {
f = _wfopen(buff2, (strcmp(mode, "r") == 0) ? L"r" : L"rb");
}
free(buff);
free(buff2);
}
delete [] buff;
delete [] buff2;
return f;
}
else
#endif
stream.open(path, mode);
return fopen(path, mode);
}
std::string& u16_u8(std::string& dest, const std::vector<w_char>& src) {
@ -217,7 +218,7 @@ int u8_u16(std::vector<w_char>& dest, const std::string& src) {
case 0xd0: { // 2-byte UTF-8 codes
if ((*(u8 + 1) & 0xc0) == 0x80) {
u2.h = (*u8 & 0x1f) >> 2;
u2.l = (static_cast<unsigned char>(*u8) << 6) + (*(u8 + 1) & 0x3f);
u2.l = (*u8 << 6) + (*(u8 + 1) & 0x3f);
++u8;
} else {
HUNSPELL_WARNING(stderr,
@ -274,35 +275,34 @@ int u8_u16(std::vector<w_char>& dest, const std::string& src) {
return dest.size();
}
namespace {
class is_any_of {
public:
explicit is_any_of(const std::string& in) : chars(in) {}
// strip strings into token based on single char delimiter
// acts like strsep() but only uses a delim char and not
// a delim string
// default delimiter: white space characters
bool operator()(char c) { return chars.find(c) != std::string::npos; }
private:
std::string chars;
};
}
std::string::const_iterator mystrsep(const std::string &str,
std::string::const_iterator& start) {
std::string::const_iterator end = str.end();
is_any_of op(" \t");
// don't use isspace() here, the string can be in some random charset
// that's way different than the locale's
std::string::const_iterator sp = start;
while (sp != end && op(*sp))
++sp;
std::string::const_iterator dp = sp;
while (dp != end && !op(*dp))
++dp;
start = dp;
return sp;
char* mystrsep(char** stringp, const char delim) {
char* mp = *stringp;
if (*mp != '\0') {
char* dp;
if (delim) {
dp = strchr(mp, delim);
} else {
// don't use isspace() here, the string can be in some random charset
// that's way different than the locale's
for (dp = mp; (*dp && *dp != ' ' && *dp != '\t'); dp++)
;
if (!*dp)
dp = NULL;
}
if (dp) {
*stringp = dp + 1;
*dp = '\0';
} else {
*stringp = mp + strlen(mp);
}
return mp;
}
return NULL;
}
// replaces strdup with ansi version
@ -320,98 +320,142 @@ char* mystrdup(const char* s) {
return d;
}
// strcat for limited length destination string
char* mystrcat(char* dest, const char* st, int max) {
int len;
int len2;
if (dest == NULL || st == NULL)
return dest;
len = strlen(dest);
len2 = strlen(st);
if (len + len2 + 1 > max)
return dest;
strcpy(dest + len, st);
return dest;
}
// remove cross-platform text line end characters
void mychomp(std::string& s) {
size_t k = s.size();
size_t newsize = k;
if ((k > 0) && ((s[k - 1] == '\r') || (s[k - 1] == '\n')))
--newsize;
if ((k > 1) && (s[k - 2] == '\r'))
--newsize;
s.resize(newsize);
void mychomp(char* s) {
size_t k = strlen(s);
if ((k > 0) && ((*(s + k - 1) == '\r') || (*(s + k - 1) == '\n')))
*(s + k - 1) = '\0';
if ((k > 1) && (*(s + k - 2) == '\r'))
*(s + k - 2) = '\0';
}
// break text to lines
std::vector<std::string> line_tok(const std::string& text, char breakchar) {
std::vector<std::string> ret;
if (text.empty()) {
return ret;
// return number of lines
int line_tok(const char* text, char*** lines, char breakchar) {
int linenum = 0;
if (!text) {
return linenum;
}
char* dup = mystrdup(text);
char* p = strchr(dup, breakchar);
while (p) {
linenum++;
*p = '\0';
p++;
p = strchr(p, breakchar);
}
linenum++;
*lines = (char**)malloc(linenum * sizeof(char*));
if (!(*lines)) {
free(dup);
return 0;
}
std::stringstream ss(text);
std::string tok;
while(std::getline(ss, tok, breakchar)) {
if (!tok.empty()) {
ret.push_back(tok);
p = dup;
int l = 0;
for (int i = 0; i < linenum; i++) {
if (*p != '\0') {
(*lines)[l] = mystrdup(p);
if (!(*lines)[l]) {
for (i = 0; i < l; i++)
free((*lines)[i]);
free(dup);
return 0;
}
l++;
}
p += strlen(p) + 1;
}
return ret;
free(dup);
if (!l) {
free(*lines);
*lines = NULL;
}
return l;
}
// uniq line in place
void line_uniq(std::string& text, char breakchar)
{
std::vector<std::string> lines = line_tok(text, breakchar);
text.clear();
if (lines.empty()) {
return;
}
text = lines[0];
for (size_t i = 1; i < lines.size(); ++i) {
bool dup = false;
for (size_t j = 0; j < i; ++j) {
if (lines[i] == lines[j]) {
dup = true;
char* line_uniq(char* text, char breakchar) {
char** lines;
int linenum = line_tok(text, &lines, breakchar);
int i;
strcpy(text, lines[0]);
for (i = 1; i < linenum; i++) {
int dup = 0;
for (int j = 0; j < i; j++) {
if (strcmp(lines[i], lines[j]) == 0) {
dup = 1;
break;
}
}
if (!dup) {
if (!text.empty())
text.push_back(breakchar);
text.append(lines[i]);
if ((i > 1) || (*(lines[0]) != '\0')) {
sprintf(text + strlen(text), "%c", breakchar);
}
strcat(text, lines[i]);
}
}
for (i = 0; i < linenum; i++) {
free(lines[i]);
}
free(lines);
return text;
}
// uniq and boundary for compound analysis: "1\n\2\n\1" -> " ( \1 | \2 ) "
void line_uniq_app(std::string& text, char breakchar) {
if (text.find(breakchar) == std::string::npos) {
return;
char* line_uniq_app(char** text, char breakchar) {
if (!strchr(*text, breakchar)) {
return *text;
}
std::vector<std::string> lines = line_tok(text, breakchar);
text.clear();
if (lines.empty()) {
return;
}
text = lines[0];
for (size_t i = 1; i < lines.size(); ++i) {
bool dup = false;
for (size_t j = 0; j < i; ++j) {
if (lines[i] == lines[j]) {
dup = true;
char** lines;
int i;
int linenum = line_tok(*text, &lines, breakchar);
int dup = 0;
for (i = 0; i < linenum; i++) {
for (int j = 0; j < (i - 1); j++) {
if (strcmp(lines[i], lines[j]) == 0) {
*(lines[i]) = '\0';
dup++;
break;
}
}
if (!dup) {
if (!text.empty())
text.push_back(breakchar);
text.append(lines[i]);
}
if ((linenum - dup) == 1) {
strcpy(*text, lines[0]);
freelist(&lines, linenum);
return *text;
}
char* newtext = (char*)malloc(strlen(*text) + 2 * linenum + 3 + 1);
if (newtext) {
free(*text);
*text = newtext;
} else {
freelist(&lines, linenum);
return *text;
}
strcpy(*text, " ( ");
for (i = 0; i < linenum; i++)
if (*(lines[i])) {
sprintf(*text + strlen(*text), "%s%s", lines[i], " | ");
}
}
if (lines.size() == 1) {
text = lines[0];
return;
}
text.assign(" ( ");
for (size_t i = 0; i < lines.size(); ++i) {
text.append(lines[i]);
text.append(" | ");
}
text[text.size() - 2] = ')'; // " ) "
(*text)[strlen(*text) - 2] = ')'; // " ) "
freelist(&lines, linenum);
return *text;
}
// append s to ends of every lines in text
@ -425,6 +469,111 @@ std::string& strlinecat(std::string& str, const std::string& apd) {
return str;
}
// morphcmp(): compare MORPH_DERI_SFX, MORPH_INFL_SFX and MORPH_TERM_SFX fields
// in the first line of the inputs
// return 0, if inputs equal
// return 1, if inputs may equal with a secondary suffix
// otherwise return -1
int morphcmp(const char* s, const char* t) {
int se = 0;
int te = 0;
const char* sl;
const char* tl;
const char* olds;
const char* oldt;
if (!s || !t)
return 1;
olds = s;
sl = strchr(s, '\n');
s = strstr(s, MORPH_DERI_SFX);
if (!s || (sl && sl < s))
s = strstr(olds, MORPH_INFL_SFX);
if (!s || (sl && sl < s)) {
s = strstr(olds, MORPH_TERM_SFX);
olds = NULL;
}
oldt = t;
tl = strchr(t, '\n');
t = strstr(t, MORPH_DERI_SFX);
if (!t || (tl && tl < t))
t = strstr(oldt, MORPH_INFL_SFX);
if (!t || (tl && tl < t)) {
t = strstr(oldt, MORPH_TERM_SFX);
oldt = NULL;
}
while (s && t && (!sl || sl > s) && (!tl || tl > t)) {
s += MORPH_TAG_LEN;
t += MORPH_TAG_LEN;
se = 0;
te = 0;
while ((*s == *t) && !se && !te) {
s++;
t++;
switch (*s) {
case ' ':
case '\n':
case '\t':
case '\0':
se = 1;
}
switch (*t) {
case ' ':
case '\n':
case '\t':
case '\0':
te = 1;
}
}
if (!se || !te) {
// not terminal suffix difference
if (olds)
return -1;
return 1;
}
olds = s;
s = strstr(s, MORPH_DERI_SFX);
if (!s || (sl && sl < s))
s = strstr(olds, MORPH_INFL_SFX);
if (!s || (sl && sl < s)) {
s = strstr(olds, MORPH_TERM_SFX);
olds = NULL;
}
oldt = t;
t = strstr(t, MORPH_DERI_SFX);
if (!t || (tl && tl < t))
t = strstr(oldt, MORPH_INFL_SFX);
if (!t || (tl && tl < t)) {
t = strstr(oldt, MORPH_TERM_SFX);
oldt = NULL;
}
}
if (!s && !t && se && te)
return 0;
return 1;
}
int get_sfxcount(const char* morph) {
if (!morph || !*morph)
return 0;
int n = 0;
const char* old = morph;
morph = strstr(morph, MORPH_DERI_SFX);
if (!morph)
morph = strstr(old, MORPH_INFL_SFX);
if (!morph)
morph = strstr(old, MORPH_TERM_SFX);
while (morph) {
n++;
old = morph;
morph = strstr(morph + 1, MORPH_DERI_SFX);
if (!morph)
morph = strstr(old + 1, MORPH_INFL_SFX);
if (!morph)
morph = strstr(old + 1, MORPH_TERM_SFX);
}
return n;
}
int fieldlen(const char* r) {
int n = 0;
while (r && *r != ' ' && *r != '\t' && *r != '\0' && *r != '\n') {
@ -466,6 +615,33 @@ std::string& mystrrep(std::string& str,
return str;
}
char* mystrrep(char* word, const char* pat, const char* rep) {
char* pos = strstr(word, pat);
if (pos) {
int replen = strlen(rep);
int patlen = strlen(pat);
while (pos) {
if (replen < patlen) {
char* end = word + strlen(word);
char* next = pos + replen;
char* prev = pos + strlen(pat);
for (; prev < end;* next = *prev, prev++, next++)
;
*next = '\0';
} else if (replen > patlen) {
char* end = pos + patlen;
char* next = word + strlen(word) + replen - patlen;
char* prev = next - replen + patlen;
for (; prev >= end;* next = *prev, prev--, next--)
;
}
strncpy(pos, rep, replen);
pos = strstr(word, pat);
}
}
return word;
}
// reverse word
size_t reverseword(std::string& word) {
std::reverse(word.begin(), word.end());
@ -481,19 +657,35 @@ size_t reverseword_utf(std::string& word) {
return w.size();
}
void uniqlist(std::vector<std::string>& list) {
if (list.size() < 2)
return;
std::vector<std::string> ret;
ret.push_back(list[0]);
for (size_t i = 1; i < list.size(); ++i) {
if (std::find(ret.begin(), ret.end(), list[i]) == ret.end())
ret.push_back(list[i]);
int uniqlist(char** list, int n) {
int i;
if (n < 2)
return n;
for (i = 0; i < n; i++) {
for (int j = 0; j < i; j++) {
if (list[j] && list[i] && (strcmp(list[j], list[i]) == 0)) {
free(list[i]);
list[i] = NULL;
break;
}
}
}
int m = 1;
for (i = 1; i < n; i++)
if (list[i]) {
list[m] = list[i];
m++;
}
return m;
}
list.swap(ret);
void freelist(char*** list, int n) {
if (list && *list) {
for (int i = 0; i < n; i++)
free((*list)[i]);
free(*list);
*list = NULL;
}
}
namespace {
@ -2265,9 +2457,9 @@ static void toAsciiLowerAndRemoveNonAlphanumeric(const char* pName,
*pBuf = '\0';
}
struct cs_info* get_current_cs(const std::string& es) {
char* normalized_encoding = new char[es.size() + 1];
toAsciiLowerAndRemoveNonAlphanumeric(es.c_str(), normalized_encoding);
struct cs_info* get_current_cs(const char* es) {
char* normalized_encoding = new char[strlen(es) + 1];
toAsciiLowerAndRemoveNonAlphanumeric(es, normalized_encoding);
struct cs_info* ccs = NULL;
int n = sizeof(encds) / sizeof(encds[0]);
@ -2282,7 +2474,7 @@ struct cs_info* get_current_cs(const std::string& es) {
if (!ccs) {
HUNSPELL_WARNING(stderr,
"error: unknown encoding %s: using %s as fallback\n", es.c_str(),
"error: unknown encoding %s: using %s as fallback\n", es,
encds[0].enc_name);
ccs = encds[0].cs_table;
}
@ -2293,7 +2485,7 @@ struct cs_info* get_current_cs(const std::string& es) {
// XXX This function was rewritten for mozilla. Instead of storing the
// conversion tables static in this file, create them when needed
// with help the mozilla backend.
struct cs_info* get_current_cs(const std::string& es) {
struct cs_info* get_current_cs(const char* es) {
struct cs_info* ccs = new cs_info[256];
// Initialze the array with dummy data so that we wouldn't need
// to return null in case of failures.
@ -2308,7 +2500,7 @@ struct cs_info* get_current_cs(const std::string& es) {
nsresult rv;
nsAutoCString label(es.c_str());
nsAutoCString label(es);
nsAutoCString encoding;
if (!EncodingUtils::FindEncodingForLabelNoReplacement(label, encoding)) {
return ccs;
@ -2373,18 +2565,21 @@ struct cs_info* get_current_cs(const std::string& es) {
#endif
// primitive isalpha() replacement for tokenization
std::string get_casechars(const char* enc) {
char* get_casechars(const char* enc) {
struct cs_info* csconv = get_current_cs(enc);
std::string expw;
for (int i = 0; i <= 255; ++i) {
char expw[MAXLNLEN];
char* p = expw;
for (int i = 0; i <= 255; i++) {
if (cupper(csconv, i) != clower(csconv, i)) {
expw.push_back(static_cast<char>(i));
*p = static_cast<char>(i);
p++;
}
}
*p = '\0';
#ifdef MOZILLA_CLIENT
delete[] csconv;
#endif
return expw;
return mystrdup(expw);
}
// language to encoding default map
@ -2411,10 +2606,10 @@ static struct lang_map lang2enc[] =
{"tr_TR", LANG_tr}, // for back-compatibility
{"ru", LANG_ru}, {"uk", LANG_uk}};
int get_lang_num(const std::string& lang) {
int get_lang_num(const char* lang) {
int n = sizeof(lang2enc) / sizeof(lang2enc[0]);
for (int i = 0; i < n; i++) {
if (strcmp(lang.c_str(), lang2enc[i].lang) == 0) {
if (strcmp(lang, lang2enc[i].lang) == 0) {
return lang2enc[i].num;
}
}
@ -2423,21 +2618,26 @@ int get_lang_num(const std::string& lang) {
#ifndef OPENOFFICEORG
#ifndef MOZILLA_CLIENT
void initialize_utf_tbl() {
int initialize_utf_tbl() {
utf_tbl_count++;
if (utf_tbl)
return;
utf_tbl = new unicode_info2[CONTSIZE];
for (size_t j = 0; j < CONTSIZE; ++j) {
utf_tbl[j].cletter = 0;
utf_tbl[j].clower = (unsigned short)j;
utf_tbl[j].cupper = (unsigned short)j;
}
for (size_t j = 0; j < UTF_LST_LEN; ++j) {
utf_tbl[utf_lst[j].c].cletter = 1;
utf_tbl[utf_lst[j].c].clower = utf_lst[j].clower;
utf_tbl[utf_lst[j].c].cupper = utf_lst[j].cupper;
}
return 0;
utf_tbl = (unicode_info2*)malloc(CONTSIZE * sizeof(unicode_info2));
if (utf_tbl) {
size_t j;
for (j = 0; j < CONTSIZE; j++) {
utf_tbl[j].cletter = 0;
utf_tbl[j].clower = (unsigned short)j;
utf_tbl[j].cupper = (unsigned short)j;
}
for (j = 0; j < UTF_LST_LEN; j++) {
utf_tbl[utf_lst[j].c].cletter = 1;
utf_tbl[utf_lst[j].c].clower = utf_lst[j].clower;
utf_tbl[utf_lst[j].c].cupper = utf_lst[j].cupper;
}
} else
return 1;
return 0;
}
#endif
#endif
@ -2446,7 +2646,7 @@ void free_utf_tbl() {
if (utf_tbl_count > 0)
utf_tbl_count--;
if (utf_tbl && (utf_tbl_count == 0)) {
delete[] utf_tbl;
free(utf_tbl);
utf_tbl = NULL;
}
}
@ -2575,6 +2775,18 @@ size_t remove_ignored_chars_utf(std::string& word,
return w2.size();
}
namespace {
class is_any_of {
public:
is_any_of(const std::string& in) : chars(in) {}
bool operator()(char c) { return chars.find(c) != std::string::npos; }
private:
std::string chars;
};
}
// strip all ignored characters in the string
size_t remove_ignored_chars(std::string& word,
const std::string& ignored_chars) {
@ -2584,48 +2796,54 @@ size_t remove_ignored_chars(std::string& word,
return word.size();
}
bool parse_string(const std::string& line, std::string& out, int ln) {
if (!out.empty()) {
HUNSPELL_WARNING(stderr, "error: line %d: multiple definitions\n", ln);
return false;
}
int parse_string(char* line, char** out, int ln) {
char* tp = line;
char* piece;
int i = 0;
int np = 0;
std::string::const_iterator iter = line.begin();
std::string::const_iterator start_piece = mystrsep(line, iter);
while (start_piece != line.end()) {
switch (i) {
case 0: {
np++;
break;
if (*out) {
HUNSPELL_WARNING(stderr, "error: line %d: multiple definitions\n", ln);
return 1;
}
piece = mystrsep(&tp, 0);
while (piece) {
if (*piece != '\0') {
switch (i) {
case 0: {
np++;
break;
}
case 1: {
*out = mystrdup(piece);
if (!*out)
return 1;
np++;
break;
}
default:
break;
}
case 1: {
out.assign(start_piece, iter);
np++;
break;
}
default:
break;
i++;
}
++i;
start_piece = mystrsep(line, iter);
// free(piece);
piece = mystrsep(&tp, 0);
}
if (np != 2) {
HUNSPELL_WARNING(stderr, "error: line %d: missing data\n", ln);
return false;
return 1;
}
return true;
return 0;
}
bool parse_array(const std::string& line,
std::string& out,
bool parse_array(char* line,
char** out,
std::vector<w_char>& out_utf16,
int utf8,
int ln) {
if (!parse_string(line, out, ln))
if (parse_string(line, out, ln))
return false;
if (utf8) {
u8_u16(out_utf16, out);
u8_u16(out_utf16, *out);
std::sort(out_utf16.begin(), out_utf16.end());
}
return true;

View File

@ -71,14 +71,13 @@
* SUCH DAMAGE.
*/
#ifndef CSUTIL_HXX_
#define CSUTIL_HXX_
#ifndef __CSUTILHXX__
#define __CSUTILHXX__
#include "hunvisapi.h"
// First some base level utility routines
#include <fstream>
#include <string>
#include <vector>
#include <string.h>
@ -128,9 +127,8 @@
#define FORBIDDENWORD 65510
#define ONLYUPCASEFLAG 65511
// fix long pathname problem of WIN32 by using w_char std::fstream::open override
LIBHUNSPELL_DLL_EXPORTED void myopen(std::ifstream& stream, const char* path,
std::ios_base::openmode mode);
// fopen or optional _wfopen to fix long pathname problem of WIN32
LIBHUNSPELL_DLL_EXPORTED FILE* myfopen(const char* path, const char* mode);
// convert UTF-16 characters to UTF-8
LIBHUNSPELL_DLL_EXPORTED std::string& u16_u8(std::string& dest,
@ -141,16 +139,21 @@ LIBHUNSPELL_DLL_EXPORTED int u8_u16(std::vector<w_char>& dest,
const std::string& src);
// remove end of line char(s)
LIBHUNSPELL_DLL_EXPORTED void mychomp(std::string& s);
LIBHUNSPELL_DLL_EXPORTED void mychomp(char* s);
// duplicate string
LIBHUNSPELL_DLL_EXPORTED char* mystrdup(const char* s);
// strcat for limited length destination string
LIBHUNSPELL_DLL_EXPORTED char* mystrcat(char* dest, const char* st, int max);
// parse into tokens with char delimiter
LIBHUNSPELL_DLL_EXPORTED std::string::const_iterator mystrsep(const std::string &str,
std::string::const_iterator& start);
LIBHUNSPELL_DLL_EXPORTED char* mystrsep(char** sptr, const char delim);
// replace pat by rep in word and return word
LIBHUNSPELL_DLL_EXPORTED char* mystrrep(char* word,
const char* pat,
const char* rep);
LIBHUNSPELL_DLL_EXPORTED std::string& mystrrep(std::string& str,
const std::string& search,
const std::string& replace);
@ -160,13 +163,13 @@ LIBHUNSPELL_DLL_EXPORTED std::string& strlinecat(std::string& str,
const std::string& apd);
// tokenize into lines with new line
LIBHUNSPELL_DLL_EXPORTED std::vector<std::string> line_tok(const std::string& text,
char breakchar);
LIBHUNSPELL_DLL_EXPORTED int line_tok(const char* text,
char*** lines,
char breakchar);
// tokenize into lines with new line and uniq in place
LIBHUNSPELL_DLL_EXPORTED void line_uniq(std::string& text, char breakchar);
LIBHUNSPELL_DLL_EXPORTED void line_uniq_app(std::string& text, char breakchar);
LIBHUNSPELL_DLL_EXPORTED char* line_uniq(char* text, char breakchar);
LIBHUNSPELL_DLL_EXPORTED char* line_uniq_app(char** text, char breakchar);
// reverse word
LIBHUNSPELL_DLL_EXPORTED size_t reverseword(std::string& word);
@ -175,7 +178,10 @@ LIBHUNSPELL_DLL_EXPORTED size_t reverseword(std::string& word);
LIBHUNSPELL_DLL_EXPORTED size_t reverseword_utf(std::string&);
// remove duplicates
LIBHUNSPELL_DLL_EXPORTED void uniqlist(std::vector<std::string>& list);
LIBHUNSPELL_DLL_EXPORTED int uniqlist(char** list, int n);
// free character array list
LIBHUNSPELL_DLL_EXPORTED void freelist(char*** list, int n);
// character encoding information
struct cs_info {
@ -184,7 +190,7 @@ struct cs_info {
unsigned char cupper;
};
LIBHUNSPELL_DLL_EXPORTED void initialize_utf_tbl();
LIBHUNSPELL_DLL_EXPORTED int initialize_utf_tbl();
LIBHUNSPELL_DLL_EXPORTED void free_utf_tbl();
LIBHUNSPELL_DLL_EXPORTED unsigned short unicodetoupper(unsigned short c,
int langnum);
@ -194,13 +200,13 @@ LIBHUNSPELL_DLL_EXPORTED unsigned short unicodetolower(unsigned short c,
int langnum);
LIBHUNSPELL_DLL_EXPORTED int unicodeisalpha(unsigned short c);
LIBHUNSPELL_DLL_EXPORTED struct cs_info* get_current_cs(const std::string& es);
LIBHUNSPELL_DLL_EXPORTED struct cs_info* get_current_cs(const char* es);
// get language identifiers of language codes
LIBHUNSPELL_DLL_EXPORTED int get_lang_num(const std::string& lang);
LIBHUNSPELL_DLL_EXPORTED int get_lang_num(const char* lang);
// get characters of the given 8bit encoding with lower- and uppercase forms
LIBHUNSPELL_DLL_EXPORTED std::string get_casechars(const char* enc);
LIBHUNSPELL_DLL_EXPORTED char* get_casechars(const char* enc);
// convert std::string to all caps
LIBHUNSPELL_DLL_EXPORTED std::string& mkallcap(std::string& s,
@ -250,12 +256,10 @@ LIBHUNSPELL_DLL_EXPORTED size_t remove_ignored_chars(
std::string& word,
const std::string& ignored_chars);
LIBHUNSPELL_DLL_EXPORTED bool parse_string(const std::string& line,
std::string& out,
int ln);
LIBHUNSPELL_DLL_EXPORTED int parse_string(char* line, char** out, int ln);
LIBHUNSPELL_DLL_EXPORTED bool parse_array(const std::string& line,
std::string& out,
LIBHUNSPELL_DLL_EXPORTED bool parse_array(char* line,
char** out,
std::vector<w_char>& out_utf16,
int utf8,
int ln);
@ -266,6 +270,10 @@ LIBHUNSPELL_DLL_EXPORTED bool copy_field(std::string& dest,
const std::string& morph,
const std::string& var);
LIBHUNSPELL_DLL_EXPORTED int morphcmp(const char* s, const char* t);
LIBHUNSPELL_DLL_EXPORTED int get_sfxcount(const char* morph);
// conversion function for protected memory
LIBHUNSPELL_DLL_EXPORTED void store_pointer(char* dest, char* source);

View File

@ -86,33 +86,33 @@ int FileMgr::fail(const char* err, const char* par) {
FileMgr::FileMgr(const char* file, const char* key) : hin(NULL), linenum(0) {
in[0] = '\0';
myopen(fin, file, std::ios_base::in);
if (!fin.is_open()) {
fin = myfopen(file, "r");
if (!fin) {
// check hzipped file
std::string st(file);
st.append(HZIP_EXTENSION);
hin = new Hunzip(st.c_str(), key);
}
if (!fin.is_open() && !hin->is_open())
if (!fin && !hin)
fail(MSG_OPEN, file);
}
FileMgr::~FileMgr() {
delete hin;
if (fin)
fclose(fin);
if (hin)
delete hin;
}
bool FileMgr::getline(std::string& dest) {
bool ret = false;
++linenum;
if (fin.is_open()) {
ret = static_cast<bool>(std::getline(fin, dest));
} else if (hin->is_open()) {
ret = hin->getline(dest);
}
if (!ret) {
--linenum;
}
return ret;
char* FileMgr::getline() {
const char* l;
linenum++;
if (fin)
return fgets(in, BUFSIZE - 1, fin);
if (hin && ((l = hin->getline()) != NULL))
return strcpy(in, l);
linenum--;
return NULL;
}
int FileMgr::getlinenum() {

View File

@ -72,21 +72,21 @@
*/
/* file manager class - read lines of files [filename] OR [filename.hz] */
#ifndef FILEMGR_HXX_
#define FILEMGR_HXX_
#ifndef _FILEMGR_HXX_
#define _FILEMGR_HXX_
#include "hunvisapi.h"
#include "hunzip.hxx"
#include <stdio.h>
#include <string>
#include <fstream>
class FileMgr {
class LIBHUNSPELL_DLL_EXPORTED FileMgr {
private:
FileMgr(const FileMgr&);
FileMgr& operator=(const FileMgr&);
protected:
std::ifstream fin;
FILE* fin;
Hunzip* hin;
char in[BUFSIZE + 50]; // input buffer
int fail(const char* err, const char* par);
@ -95,7 +95,7 @@ class FileMgr {
public:
FileMgr(const char* filename, const char* key = NULL);
~FileMgr();
bool getline(std::string&);
char* getline();
int getlinenum();
};
#endif

File diff suppressed because it is too large Load Diff

View File

@ -71,8 +71,10 @@
* SUCH DAMAGE.
*/
#ifndef HASHMGR_HXX_
#define HASHMGR_HXX_
#ifndef _HASHMGR_HXX_
#define _HASHMGR_HXX_
#include "hunvisapi.h"
#include <stdio.h>
#include <string>
@ -84,7 +86,7 @@
enum flag { FLAG_CHAR, FLAG_LONG, FLAG_NUM, FLAG_UNI };
class HashMgr {
class LIBHUNSPELL_DLL_EXPORTED HashMgr {
int tablesize;
struct hentry** tableptr;
flag flag_mode;
@ -92,10 +94,10 @@ class HashMgr {
int utf8;
unsigned short forbiddenword;
int langnum;
std::string enc;
std::string lang;
char* enc;
char* lang;
struct cs_info* csconv;
std::string ignorechars;
char* ignorechars;
std::vector<w_char> ignorechars_utf16;
int numaliasf; // flag vector `compression' with aliases
unsigned short** aliasf;
@ -112,35 +114,35 @@ class HashMgr {
struct hentry* walk_hashtable(int& col, struct hentry* hp) const;
int add(const std::string& word);
int add_with_affix(const std::string& word, const std::string& pattern);
int remove(const std::string& word);
int decode_flags(unsigned short** result, const std::string& flags, FileMgr* af) const;
bool decode_flags(std::vector<unsigned short>& result, const std::string& flags, FileMgr* af) const;
unsigned short decode_flag(const char* flag) const;
char* encode_flag(unsigned short flag) const;
int is_aliasf() const;
int get_aliasf(int index, unsigned short** fvec, FileMgr* af) const;
int is_aliasm() const;
char* get_aliasm(int index) const;
int add_with_affix(const char* word, const char* pattern);
int remove(const char* word);
int decode_flags(unsigned short** result, char* flags, FileMgr* af);
unsigned short decode_flag(const char* flag);
char* encode_flag(unsigned short flag);
int is_aliasf();
int get_aliasf(int index, unsigned short** fvec, FileMgr* af);
int is_aliasm();
char* get_aliasm(int index);
private:
int get_clen_and_captype(const std::string& word, int* captype);
int load_tables(const char* tpath, const char* key);
int add_word(const std::string& word,
int add_word(const char* word,
int wbl,
int wcl,
unsigned short* ap,
int al,
const std::string* desc,
const char* desc,
bool onlyupcase);
int load_config(const char* affpath, const char* key);
bool parse_aliasf(const std::string& line, FileMgr* af);
int parse_aliasf(char* line, FileMgr* af);
int add_hidden_capitalized_word(const std::string& word,
int wcl,
unsigned short* flags,
int al,
const std::string* dp,
char* dp,
int captype);
bool parse_aliasm(const std::string& line, FileMgr* af);
int parse_aliasm(char* line, FileMgr* af);
int remove_forbidden_flag(const std::string& word);
};

View File

@ -38,8 +38,8 @@
*
* ***** END LICENSE BLOCK ***** */
#ifndef HTYPES_HXX_
#define HTYPES_HXX_
#ifndef _HTYPES_HXX_
#define _HTYPES_HXX_
#define ROTATE_LEN 5

File diff suppressed because it is too large Load Diff

View File

@ -38,8 +38,8 @@
*
* ***** END LICENSE BLOCK ***** */
#ifndef MYSPELLMGR_H_
#define MYSPELLMGR_H_
#ifndef _MYSPELLMGR_H_
#define _MYSPELLMGR_H_
#include "hunvisapi.h"
@ -68,7 +68,7 @@ LIBHUNSPELL_DLL_EXPORTED int Hunspell_add_dic(Hunhandle* pHunspell,
*/
LIBHUNSPELL_DLL_EXPORTED int Hunspell_spell(Hunhandle* pHunspell, const char*);
LIBHUNSPELL_DLL_EXPORTED const char* Hunspell_get_dic_encoding(Hunhandle* pHunspell);
LIBHUNSPELL_DLL_EXPORTED char* Hunspell_get_dic_encoding(Hunhandle* pHunspell);
/* suggest(suggestions, word) - search suggestions
* input: pointer to an array of strings pointer and the (bad) word

View File

@ -70,29 +70,26 @@
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
#ifndef MYSPELLMGR_HXX_
#define MYSPELLMGR_HXX_
#include "hunvisapi.h"
#include "w_char.hxx"
#include <string>
#include "hashmgr.hxx"
#include "affixmgr.hxx"
#include "suggestmgr.hxx"
#include "langnum.hxx"
#include <vector>
#define SPELL_XML "<?xml?>"
#define MAXDIC 20
#define MAXSUGGESTION 15
#define MAXSHARPS 5
#define MAXWORDLEN 176
#if __GNUC__ > 3 || (__GNUC__ == 3 && __GNUC_MINOR__ >= 1)
# define H_DEPRECATED __attribute__((__deprecated__))
#elif defined(_MSC_VER) && (_MSC_VER >= 1300)
# define H_DEPRECATED __declspec(deprecated)
#else
# define H_DEPRECATED
#endif
#define HUNSPELL_OK (1 << 0)
#define HUNSPELL_OK_WARN (1 << 1)
class HunspellImpl;
#ifndef _MYSPELLMGR_HXX_
#define _MYSPELLMGR_HXX_
class LIBHUNSPELL_DLL_EXPORTED Hunspell {
private:
@ -100,7 +97,17 @@ class LIBHUNSPELL_DLL_EXPORTED Hunspell {
Hunspell& operator=(const Hunspell&);
private:
HunspellImpl* m_Impl;
AffixMgr* pAMgr;
HashMgr* pHMgr[MAXDIC];
int maxdic;
SuggestMgr* pSMgr;
char* affixpath;
char* encoding;
struct cs_info* csconv;
int langnum;
int utf8;
int complexprefixes;
char** wordbreak;
public:
/* Hunspell(aff, dic) - constructor of Hunspell class
@ -111,6 +118,7 @@ class LIBHUNSPELL_DLL_EXPORTED Hunspell {
* long path names (without the long path prefix Hunspell will use fopen()
* with system-dependent character encoding instead of _wfopen()).
*/
Hunspell(const char* affpath, const char* dpath, const char* key = NULL);
~Hunspell();
@ -118,7 +126,7 @@ class LIBHUNSPELL_DLL_EXPORTED Hunspell {
int add_dic(const char* dpath, const char* key = NULL);
/* spell(word) - spellcheck word
* output: false = bad word, true = good word
* output: 0 = bad word, not 0 = good word
*
* plus output:
* info: information bit array, fields:
@ -126,8 +134,8 @@ class LIBHUNSPELL_DLL_EXPORTED Hunspell {
* SPELL_FORBIDDEN = an explicit forbidden word
* root: root (stem), when input is a word with affix(es)
*/
bool spell(const std::string& word, int* info = NULL, std::string* root = NULL);
H_DEPRECATED int spell(const char* word, int* info = NULL, char** root = NULL);
int spell(const char* word, int* info = NULL, char** root = NULL);
/* suggest(suggestions, word) - search suggestions
* input: pointer to an array of strings pointer and the (bad) word
@ -136,8 +144,8 @@ class LIBHUNSPELL_DLL_EXPORTED Hunspell {
* a newly allocated array of strings (*slts will be NULL when number
* of suggestion equals 0.)
*/
std::vector<std::string> suggest(const std::string& word);
H_DEPRECATED int suggest(char*** slst, const char* word);
int suggest(char*** slst, const char* word);
/* Suggest words from suffix rules
* suffix_suggest(suggestions, root_word)
@ -147,37 +155,36 @@ class LIBHUNSPELL_DLL_EXPORTED Hunspell {
* a newly allocated array of strings (*slts will be NULL when number
* of suggestion equals 0.)
*/
std::vector<std::string> suffix_suggest(const std::string& root_word);
H_DEPRECATED int suffix_suggest(char*** slst, const char* root_word);
int suffix_suggest(char*** slst, const char* root_word);
/* deallocate suggestion lists */
H_DEPRECATED void free_list(char*** slst, int n);
const std::string& get_dict_encoding() const;
H_DEPRECATED const char* get_dic_encoding() const;
void free_list(char*** slst, int n);
char* get_dic_encoding();
/* morphological functions */
/* analyze(result, word) - morphological analysis of the word */
std::vector<std::string> analyze(const std::string& word);
H_DEPRECATED int analyze(char*** slst, const char* word);
/* stem(word) - stemmer function */
std::vector<std::string> stem(const std::string& word);
H_DEPRECATED int stem(char*** slst, const char* word);
int analyze(char*** slst, const char* word);
/* stem(analysis, n) - get stems from a morph. analysis
/* stem(result, word) - stemmer function */
int stem(char*** slst, const char* word);
/* stem(result, analysis, n) - get stems from a morph. analysis
* example:
* char ** result, result2;
* int n1 = analyze(&result, "words");
* int n2 = stem(&result2, result, n1);
*/
std::vector<std::string> stem(const std::vector<std::string>& morph);
H_DEPRECATED int stem(char*** slst, char** morph, int n);
int stem(char*** slst, char** morph, int n);
/* generate(result, word, word2) - morphological generation by example(s) */
std::vector<std::string> generate(const std::string& word, const std::string& word2);
H_DEPRECATED int generate(char*** slst, const char* word, const char* word2);
int generate(char*** slst, const char* word, const char* word2);
/* generate(result, word, desc, n) - generation by morph. description(s)
* example:
@ -186,38 +193,66 @@ class LIBHUNSPELL_DLL_EXPORTED Hunspell {
* int n = generate(&result, "word", &affix, 1);
* for (int i = 0; i < n; i++) printf("%s\n", result[i]);
*/
std::vector<std::string> generate(const std::string& word, const std::vector<std::string>& pl);
H_DEPRECATED int generate(char*** slst, const char* word, char** desc, int n);
int generate(char*** slst, const char* word, char** desc, int n);
/* functions for run-time modification of the dictionary */
/* add word to the run-time dictionary */
int add(const std::string& word);
int add(const char* word);
/* add word to the run-time dictionary with affix flags of
* the example (a dictionary word): Hunspell will recognize
* affixed forms of the new word, too.
*/
int add_with_affix(const std::string& word, const std::string& example);
int add_with_affix(const char* word, const char* example);
/* remove word from the run-time dictionary */
int remove(const std::string& word);
int remove(const char* word);
/* other */
/* get extra word characters definied in affix file for tokenization */
const std::string& get_wordchars() const;
const std::vector<w_char>& get_wordchars_utf16() const;
const char* get_wordchars();
const std::vector<w_char>& get_wordchars_utf16();
const std::string& get_version() const;
struct cs_info* get_csconv();
const char* get_version();
int get_langnum() const;
/* need for putdic */
bool input_conv(const std::string& word, std::string& dest);
int input_conv(const char* word, char* dest, size_t destsize);
private:
void cleanword(std::string& dest, const char*, int* pcaptype, int* pabbrev);
size_t cleanword2(std::string& dest,
std::vector<w_char>& dest_u,
const char*,
int* w_len,
int* pcaptype,
size_t* pabbrev);
void mkinitcap(std::string& u8);
int mkinitcap2(std::string& u8, std::vector<w_char>& u16);
int mkinitsmall2(std::string& u8, std::vector<w_char>& u16);
void mkallcap(std::string& u8);
int mkallsmall2(std::string& u8, std::vector<w_char>& u16);
struct hentry* checkword(const char*, int* info, char** root);
std::string sharps_u8_l1(const std::string& source);
hentry*
spellsharps(std::string& base, size_t start_pos, int, int, int* info, char** root);
int is_keepcase(const hentry* rv);
int insert_sug(char*** slst, const char* word, int ns);
void cat_result(std::string& result, char* st);
char* stem_description(const char* desc);
int spellml(char*** slst, const char* word);
std::string get_xml_par(const char* par);
const char* get_xml_pos(const char* s, const char* attr);
int get_xml_list(char*** slst, const char* list, const char* tag);
int check_xml_par(const char* q, const char* attr, const char* value);
};
#endif

View File

@ -1,5 +1,5 @@
#ifndef HUNSPELL_VISIBILITY_H_
#define HUNSPELL_VISIBILITY_H_
#ifndef _HUNSPELL_VISIBILITY_H_
#define _HUNSPELL_VISIBILITY_H_
#if defined(HUNSPELL_STATIC)
# define LIBHUNSPELL_DLL_EXPORTED

View File

@ -59,7 +59,7 @@ int Hunzip::fail(const char* err, const char* par) {
}
Hunzip::Hunzip(const char* file, const char* key)
: bufsiz(0), lastbit(0), inc(0), inbits(0), outc(0) {
: fin(NULL), bufsiz(0), lastbit(0), inc(0), inbits(0), outc(0), dec(NULL) {
in[0] = out[0] = line[0] = '\0';
filename = mystrdup(file);
if (getcode(key) == -1)
@ -70,19 +70,19 @@ Hunzip::Hunzip(const char* file, const char* key)
int Hunzip::getcode(const char* key) {
unsigned char c[2];
int i, j, n;
int i, j, n, p;
int allocatedbit = BASEBITREC;
const char* enc = key;
if (!filename)
return -1;
myopen(fin, filename, std::ios_base::in | std::ios_base::binary);
if (!fin.is_open())
fin = myfopen(filename, "rb");
if (!fin)
return -1;
// read magic number
if (!fin.read(in, 3) ||
if ((fread(in, 1, 3, fin) < MAGICLEN) ||
!(strncmp(MAGIC, in, MAGICLEN) == 0 ||
strncmp(MAGIC_ENCRYPT, in, MAGICLEN) == 0)) {
return fail(MSG_FORMAT, filename);
@ -93,7 +93,7 @@ int Hunzip::getcode(const char* key) {
unsigned char cs;
if (!key)
return fail(MSG_KEY, filename);
if (!fin.read(reinterpret_cast<char*>(c), 1))
if (fread(&c, 1, 1, fin) < 1)
return fail(MSG_FORMAT, filename);
for (cs = 0; *enc; enc++)
cs ^= *enc;
@ -104,7 +104,7 @@ int Hunzip::getcode(const char* key) {
key = NULL;
// read record count
if (!fin.read(reinterpret_cast<char*>(c), 2))
if (fread(&c, 1, 2, fin) < 2)
return fail(MSG_FORMAT, filename);
if (key) {
@ -115,14 +115,16 @@ int Hunzip::getcode(const char* key) {
}
n = ((int)c[0] << 8) + c[1];
dec.resize(BASEBITREC);
dec = (struct bit*)malloc(BASEBITREC * sizeof(struct bit));
if (!dec)
return fail(MSG_MEMORY, filename);
dec[0].v[0] = 0;
dec[0].v[1] = 0;
// read codes
for (i = 0; i < n; i++) {
unsigned char l;
if (!fin.read(reinterpret_cast<char*>(c), 2))
if (fread(c, 1, 2, fin) < 2)
return fail(MSG_FORMAT, filename);
if (key) {
if (*(++enc) == '\0')
@ -132,14 +134,14 @@ int Hunzip::getcode(const char* key) {
enc = key;
c[1] ^= *enc;
}
if (!fin.read(reinterpret_cast<char*>(&l), 1))
if (fread(&l, 1, 1, fin) < 1)
return fail(MSG_FORMAT, filename);
if (key) {
if (*(++enc) == '\0')
enc = key;
l ^= *enc;
}
if (!fin.read(in, l / 8 + 1))
if (fread(in, 1, l / 8 + 1, fin) < (size_t)l / 8 + 1)
return fail(MSG_FORMAT, filename);
if (key)
for (j = 0; j <= l / 8; j++) {
@ -147,7 +149,7 @@ int Hunzip::getcode(const char* key) {
enc = key;
in[j] ^= *enc;
}
int p = 0;
p = 0;
for (j = 0; j < l; j++) {
int b = (in[j / 8] & (1 << (7 - (j % 8)))) ? 1 : 0;
int oldp = p;
@ -156,7 +158,7 @@ int Hunzip::getcode(const char* key) {
lastbit++;
if (lastbit == allocatedbit) {
allocatedbit += BASEBITREC;
dec.resize(allocatedbit);
dec = (struct bit*)realloc(dec, allocatedbit * sizeof(struct bit));
}
dec[lastbit].v[0] = 0;
dec[lastbit].v[1] = 0;
@ -171,6 +173,10 @@ int Hunzip::getcode(const char* key) {
}
Hunzip::~Hunzip() {
if (dec)
free(dec);
if (fin)
fclose(fin);
if (filename)
free(filename);
}
@ -179,17 +185,16 @@ int Hunzip::getbuf() {
int p = 0;
int o = 0;
do {
if (inc == 0) {
fin.read(in, BUFSIZE);
inbits = fin.gcount() * 8;
}
if (inc == 0)
inbits = fread(in, 1, BUFSIZE, fin) * 8;
for (; inc < inbits; inc++) {
int b = (in[inc / 8] & (1 << (7 - (inc % 8)))) ? 1 : 0;
int oldp = p;
p = dec[p].v[b];
if (p == 0) {
if (oldp == lastbit) {
fin.close();
fclose(fin);
fin = NULL;
// add last odd byte
if (dec[lastbit].c[0])
out[o++] = dec[lastbit].c[1];
@ -207,11 +212,11 @@ int Hunzip::getbuf() {
return fail(MSG_FORMAT, filename);
}
bool Hunzip::getline(std::string& dest) {
const char* Hunzip::getline() {
char linebuf[BUFSIZE];
int l = 0, eol = 0, left = 0, right = 0;
if (bufsiz == -1)
return false;
return NULL;
while (l < bufsiz && !eol) {
linebuf[l++] = out[outc];
switch (out[outc]) {
@ -246,7 +251,7 @@ bool Hunzip::getline(std::string& dest) {
}
if (++outc == bufsiz) {
outc = 0;
bufsiz = fin.is_open() ? getbuf() : -1;
bufsiz = fin ? getbuf() : -1;
}
}
if (right)
@ -254,6 +259,5 @@ bool Hunzip::getline(std::string& dest) {
else
linebuf[l] = '\0';
strcpy(line + left, linebuf);
dest.assign(line);
return true;
return line;
}

View File

@ -41,14 +41,12 @@
/* hunzip: file decompression for sorted dictionaries with optional encryption,
* algorithm: prefix-suffix encoding and 16-bit Huffman encoding */
#ifndef HUNZIP_HXX_
#define HUNZIP_HXX_
#ifndef _HUNZIP_HXX_
#define _HUNZIP_HXX_
#include "hunvisapi.h"
#include <stdio.h>
#include <fstream>
#include <vector>
#define BUFSIZE 65536
#define HZIP_EXTENSION ".hz"
@ -70,9 +68,9 @@ class LIBHUNSPELL_DLL_EXPORTED Hunzip {
protected:
char* filename;
std::ifstream fin;
FILE* fin;
int bufsiz, lastbit, inc, inbits, outc;
std::vector<bit> dec; // code table
struct bit* dec; // code table
char in[BUFSIZE]; // input buffer
char out[BUFSIZE + 1]; // Huffman-decoded buffer
char line[BUFSIZE + 50]; // decoded line
@ -83,8 +81,7 @@ class LIBHUNSPELL_DLL_EXPORTED Hunzip {
public:
Hunzip(const char* filename, const char* key = NULL);
~Hunzip();
bool is_open() { return fin.is_open(); }
bool getline(std::string& dest);
const char* getline();
};
#endif

View File

@ -38,12 +38,12 @@
*
* ***** END LICENSE BLOCK ***** */
#ifndef LANGNUM_HXX_
#define LANGNUM_HXX_
#ifndef _LANGNUM_HXX_
#define _LANGNUM_HXX_
/*
language numbers for language specific codes
see https://wiki.openoffice.org/w/index.php?title=Languages&oldid=230199
see http://l10n.openoffice.org/languages.html
*/
enum {

View File

@ -36,13 +36,15 @@
#include "phonet.hxx"
void init_phonet_hash(phonetable& parms) {
for (int i = 0; i < HASHSIZE; i++) {
int i, k;
for (i = 0; i < HASHSIZE; i++) {
parms.hash[i] = -1;
}
for (int i = 0; parms.rules[i][0] != '\0'; i += 2) {
for (i = 0; parms.rules[i][0] != '\0'; i += 2) {
/** set hash value **/
int k = (unsigned char)parms.rules[i][0];
k = (unsigned char)parms.rules[i][0];
if (parms.hash[k] < 0) {
parms.hash[k] = i;
@ -71,8 +73,9 @@ static int myisalpha(char ch) {
std::string phonet(const std::string& inword, phonetable& parms) {
int i, k = 0, p, z;
int k0, n0, p0 = -333;
int k0, n0, p0 = -333, z0;
char c;
const char* s;
typedef unsigned char uchar;
size_t len = inword.size();
@ -87,15 +90,15 @@ std::string phonet(const std::string& inword, phonetable& parms) {
i = z = 0;
while ((c = word[i]) != '\0') {
int n = parms.hash[(uchar)c];
int z0 = 0;
z0 = 0;
if (n >= 0 && !parms.rules[n].empty()) {
if (n >= 0) {
/** check all rules for the same letter **/
while (parms.rules[n][0] == c) {
/** check whole string **/
k = 1; /** number of found letters **/
p = 5; /** default priority **/
const char*s = parms.rules[n].c_str();
s = parms.rules[n];
s++; /** important for (see below) "*(s-1)" **/
while (*s != '\0' && word[i + k] == *s && !isdigit((unsigned char)*s) &&
@ -139,13 +142,13 @@ std::string phonet(const std::string& inword, phonetable& parms) {
n0 = parms.hash[(uchar)c0];
// if (parms.followup && k > 1 && n0 >= 0
if (k > 1 && n0 >= 0 && p0 != (int)'-' && word[i + k] != '\0' && !parms.rules[n0].empty()) {
if (k > 1 && n0 >= 0 && p0 != (int)'-' && word[i + k] != '\0') {
/** test follow-up rule for "word[i+k]" **/
while (parms.rules[n0][0] == c0) {
/** check whole string **/
k0 = k;
p0 = 5;
s = parms.rules[n0].c_str();
s = parms.rules[n0];
s++;
while (*s != '\0' && word[i + k0] == *s &&
!isdigit((unsigned char)*s) &&
@ -203,9 +206,9 @@ std::string phonet(const std::string& inword, phonetable& parms) {
} /** end of follow-up stuff **/
/** replace string **/
s = parms.rules[n + 1].c_str();
p0 = (!parms.rules[n].empty() &&
strchr(parms.rules[n].c_str() + 1, '<') != NULL)
s = parms.rules[n + 1];
p0 = (parms.rules[n][0] != '\0' &&
strchr(parms.rules[n] + 1, '<') != NULL)
? 1
: 0;
if (p0 == 1 && z == 0) {
@ -238,8 +241,8 @@ std::string phonet(const std::string& inword, phonetable& parms) {
}
/** new "actual letter" **/
c = *s;
if (!parms.rules[n].empty() &&
strstr(parms.rules[n].c_str() + 1, "^^") != NULL) {
if (parms.rules[n][0] != '\0' &&
strstr(parms.rules[n] + 1, "^^") != NULL) {
if (c != '\0') {
target.push_back(c);
}

View File

@ -27,8 +27,8 @@
Porting from Aspell to Hunspell using C-like structs
*/
#ifndef PHONET_HXX_
#define PHONET_HXX_
#ifndef __PHONETHXX__
#define __PHONETHXX__
#define HASHSIZE 256
#define MAXPHONETLEN 256
@ -38,7 +38,9 @@
struct phonetable {
char utf8;
std::vector<std::string> rules;
cs_info* lang;
int num;
char** rules;
int hash[HASHSIZE];
};

View File

@ -90,122 +90,104 @@ RepList::RepList(int n) {
RepList::~RepList() {
for (int i = 0; i < pos; i++) {
delete dat[i];
free(dat[i]->pattern);
free(dat[i]->pattern2);
free(dat[i]);
}
free(dat);
}
int RepList::get_pos() {
return pos;
}
replentry* RepList::item(int n) {
return dat[n];
}
int RepList::find(const char* word) {
int RepList::near(const char* word) {
int p1 = 0;
int p2 = pos - 1;
while (p1 <= p2) {
int p2 = pos;
while ((p2 - p1) > 1) {
int m = (p1 + p2) / 2;
int c = strncmp(word, dat[m]->pattern.c_str(), dat[m]->pattern.size());
if (c < 0)
p2 = m - 1;
else if (c > 0)
p1 = m + 1;
else { // scan back for a longer match
for (p1 = m - 1; p1 >= 0; --p1)
if (!strncmp(word, dat[p1]->pattern.c_str(), dat[p1]->pattern.size()))
m = p1;
else if (dat[p1]->pattern.size() < dat[m]->pattern.size())
break;
return m;
}
int c = strcmp(word, dat[m]->pattern);
if (c <= 0) {
if (c < 0)
p2 = m;
else
p1 = p2 = m;
} else
p1 = m;
}
return -1;
return p1;
}
std::string RepList::replace(const char* word, int ind, bool atstart) {
int type = atstart ? 1 : 0;
if (ind < 0)
return std::string();
if (strlen(word) == dat[ind]->pattern.size())
type = atstart ? 3 : 2;
while (type && dat[ind]->outstrings[type].empty())
type = (type == 2 && !atstart) ? 0 : type - 1;
return dat[ind]->outstrings[type];
}
int RepList::add(const std::string& in_pat1, const std::string& pat2) {
if (pos >= size || in_pat1.empty() || pat2.empty()) {
return 1;
}
// analyse word context
int type = 0;
std::string pat1(in_pat1);
if (pat1[0] == '_') {
pat1.erase(0, 1);
type = 1;
}
if (!pat1.empty() && pat1[pat1.size() - 1] == '_') {
type = type + 2;
pat1.erase(pat1.size() - 1);
}
mystrrep(pat1, "_", " ");
// find existing entry
int m = find(pat1.c_str());
if (m >= 0 && dat[m]->pattern == pat1) {
// since already used
dat[m]->outstrings[type] = pat2;
mystrrep(dat[m]->outstrings[type], "_", " ");
return 0;
}
// make a new entry if none exists
replentry* r = new replentry;
if (r == NULL)
return 1;
r->pattern = pat1;
r->outstrings[type] = pat2;
mystrrep(r->outstrings[type], "_", " ");
dat[pos++] = r;
// sort to the right place in the list
int i;
for (i = pos - 1; i > 0; i--) {
int c = strncmp(r->pattern.c_str(), dat[i-1]->pattern.c_str(), dat[i-1]->pattern.size());
if (c > 0)
break;
else if (c == 0) { // subpatterns match. Patterns can't be identical since would catch earlier
for (int j = i - 2; j > 0 && !strncmp(dat[i-1]->pattern.c_str(), dat[j]->pattern.c_str(), dat[i-1]->pattern.size()); --j)
if (dat[j]->pattern.size() > r->pattern.size() ||
(dat[j]->pattern.size() == r->pattern.size() && strncmp(dat[j]->pattern.c_str(), r->pattern.c_str(), r->pattern.size()) > 0)) {
i = j;
break;
}
break;
}
}
memmove(dat + i + 1, dat + i, (pos - i - 1) * sizeof(replentry *));
dat[i] = r;
int RepList::match(const char* word, int n) {
if (strncmp(word, dat[n]->pattern, strlen(dat[n]->pattern)) == 0)
return strlen(dat[n]->pattern);
return 0;
}
bool RepList::conv(const std::string& in_word, std::string& dest) {
int RepList::add(char* pat1, char* pat2) {
if (pos >= size || pat1 == NULL || pat2 == NULL)
return 1;
replentry* r = (replentry*)malloc(sizeof(replentry));
if (r == NULL)
return 1;
r->pattern = mystrrep(pat1, "_", " ");
r->pattern2 = mystrrep(pat2, "_", " ");
r->start = false;
r->end = false;
dat[pos++] = r;
for (int i = pos - 1; i > 0; i--) {
r = dat[i];
if (strcmp(r->pattern, dat[i - 1]->pattern) < 0) {
dat[i] = dat[i - 1];
dat[i - 1] = r;
} else
break;
}
return 0;
}
int RepList::conv(const char* word, char* dest, size_t destsize) {
size_t stl = 0;
int change = 0;
for (size_t i = 0; i < strlen(word); i++) {
int n = near(word + i);
int l = match(word + i, n);
if (l) {
size_t replen = strlen(dat[n]->pattern2);
if (stl + replen >= destsize)
return -1;
strcpy(dest + stl, dat[n]->pattern2);
stl += replen;
i += l - 1;
change = 1;
} else {
if (stl + 1 >= destsize)
return -1;
dest[stl++] = word[i];
}
}
dest[stl] = '\0';
return change;
}
bool RepList::conv(const char* word, std::string& dest) {
dest.clear();
size_t wordlen = in_word.size();
const char* word = in_word.c_str();
bool change = false;
for (size_t i = 0; i < wordlen; ++i) {
int n = find(word + i);
std::string l = replace(word + i, n, i == 0);
if (!l.empty()) {
dest.append(l);
i += dat[n]->pattern.size() - 1;
for (size_t i = 0; i < strlen(word); i++) {
int n = near(word + i);
int l = match(word + i, n);
if (l) {
dest.append(dat[n]->pattern2);
i += l - 1;
change = true;
} else {
dest.push_back(word[i]);
}
}
return change;
}

View File

@ -72,15 +72,17 @@
*/
/* string replacement list class */
#ifndef REPLIST_HXX_
#define REPLIST_HXX_
#ifndef _REPLIST_HXX_
#define _REPLIST_HXX_
#include "hunvisapi.h"
#include "w_char.hxx"
#include <string>
#include <vector>
class RepList {
class LIBHUNSPELL_DLL_EXPORTED RepList {
private:
RepList(const RepList&);
RepList& operator=(const RepList&);
@ -91,13 +93,15 @@ class RepList {
int pos;
public:
explicit RepList(int n);
RepList(int n);
~RepList();
int add(const std::string& pat1, const std::string& pat2);
int get_pos();
int add(char* pat1, char* pat2);
replentry* item(int n);
int find(const char* word);
std::string replace(const char* word, int n, bool atstart);
bool conv(const std::string& word, std::string& dest);
int near(const char* word);
int match(const char* word, int n);
int conv(const char* word, char* dest, size_t destsize);
bool conv(const char* word, std::string& dest);
};
#endif

File diff suppressed because it is too large Load Diff

View File

@ -71,8 +71,8 @@
* SUCH DAMAGE.
*/
#ifndef SUGGESTMGR_HXX_
#define SUGGESTMGR_HXX_
#ifndef _SUGGESTMGR_HXX_
#define _SUGGESTMGR_HXX_
#define MAX_ROOTS 100
#define MAX_WORDS 100
@ -91,6 +91,8 @@
#define NGRAM_LOWERING (1 << 2)
#define NGRAM_WEIGHTED (1 << 3)
#include "hunvisapi.h"
#include "atypes.hxx"
#include "affixmgr.hxx"
#include "hashmgr.hxx"
@ -99,22 +101,22 @@
enum { LCS_UP, LCS_LEFT, LCS_UPLEFT };
class SuggestMgr {
class LIBHUNSPELL_DLL_EXPORTED SuggestMgr {
private:
SuggestMgr(const SuggestMgr&);
SuggestMgr& operator=(const SuggestMgr&);
private:
char* ckey;
size_t ckeyl;
std::vector<w_char> ckey_utf;
int ckeyl;
w_char* ckey_utf;
char* ctry;
size_t ctryl;
std::vector<w_char> ctry_utf;
int ctryl;
w_char* ctry_utf;
AffixMgr* pAMgr;
unsigned int maxSug;
int maxSug;
struct cs_info* csconv;
int utf8;
int langnum;
@ -124,53 +126,62 @@ class SuggestMgr {
int complexprefixes;
public:
SuggestMgr(const char* tryme, unsigned int maxn, AffixMgr* aptr);
SuggestMgr(const char* tryme, int maxn, AffixMgr* aptr);
~SuggestMgr();
void suggest(std::vector<std::string>& slst, const char* word, int* onlycmpdsug);
void ngsuggest(std::vector<std::string>& slst, const char* word, const std::vector<HashMgr*>& rHMgr);
int suggest(char*** slst, const char* word, int nsug, int* onlycmpdsug);
int ngsuggest(char** wlst, const char* word, int ns, HashMgr** pHMgr, int md);
int suggest_auto(char*** slst, const char* word, int nsug);
int suggest_stems(char*** slst, const char* word, int nsug);
int suggest_pos_stems(char*** slst, const char* word, int nsug);
std::string suggest_morph(const std::string& word);
std::string suggest_gen(const std::vector<std::string>& pl, const std::string& pattern);
char* suggest_morph(const char* word);
char* suggest_gen(char** pl, int pln, const char* pattern);
char* suggest_morph_for_spelling_error(const char* word);
private:
void testsug(std::vector<std::string>& wlst,
const std::string& candidate,
int cpdsuggest,
int* timer,
clock_t* timelimit);
int checkword(const std::string& word, int, int*, clock_t*);
int testsug(char** wlst,
const char* candidate,
int wl,
int ns,
int cpdsuggest,
int* timer,
clock_t* timelimit);
int checkword(const char*, int, int, int*, clock_t*);
int check_forbidden(const char*, int);
void capchars(std::vector<std::string>&, const char*, int);
int replchars(std::vector<std::string>&, const char*, int);
int doubletwochars(std::vector<std::string>&, const char*, int);
int forgotchar(std::vector<std::string>&, const char*, int);
int swapchar(std::vector<std::string>&, const char*, int);
int longswapchar(std::vector<std::string>&, const char*, int);
int movechar(std::vector<std::string>&, const char*, int);
int extrachar(std::vector<std::string>&, const char*, int);
int badcharkey(std::vector<std::string>&, const char*, int);
int badchar(std::vector<std::string>&, const char*, int);
int twowords(std::vector<std::string>&, const char*, int);
int capchars(char**, const char*, int, int);
int replchars(char**, const char*, int, int);
int doubletwochars(char**, const char*, int, int);
int forgotchar(char**, const char*, int, int);
int swapchar(char**, const char*, int, int);
int longswapchar(char**, const char*, int, int);
int movechar(char**, const char*, int, int);
int extrachar(char**, const char*, int, int);
int badcharkey(char**, const char*, int, int);
int badchar(char**, const char*, int, int);
int twowords(char**, const char*, int, int);
int fixstems(char**, const char*, int);
void capchars_utf(std::vector<std::string>&, const w_char*, int wl, int);
int doubletwochars_utf(std::vector<std::string>&, const w_char*, int wl, int);
int forgotchar_utf(std::vector<std::string>&, const w_char*, int wl, int);
int extrachar_utf(std::vector<std::string>&, const w_char*, int wl, int);
int badcharkey_utf(std::vector<std::string>&, const w_char*, int wl, int);
int badchar_utf(std::vector<std::string>&, const w_char*, int wl, int);
int swapchar_utf(std::vector<std::string>&, const w_char*, int wl, int);
int longswapchar_utf(std::vector<std::string>&, const w_char*, int, int);
int movechar_utf(std::vector<std::string>&, const w_char*, int, int);
int capchars_utf(char**, const w_char*, int wl, int, int);
int doubletwochars_utf(char**, const w_char*, int wl, int, int);
int forgotchar_utf(char**, const w_char*, int wl, int, int);
int extrachar_utf(char**, const w_char*, int wl, int, int);
int badcharkey_utf(char**, const w_char*, int wl, int, int);
int badchar_utf(char**, const w_char*, int wl, int, int);
int swapchar_utf(char**, const w_char*, int wl, int, int);
int longswapchar_utf(char**, const w_char*, int, int, int);
int movechar_utf(char**, const w_char*, int, int, int);
int mapchars(std::vector<std::string>&, const char*, int);
int mapchars(char**, const char*, int, int);
int map_related(const char*,
std::string&,
int,
std::vector<std::string>& wlst,
char** wlst,
int,
int,
const mapentry*,
int,
const std::vector<mapentry>&,
int*,
clock_t*);
int ngram(int n, const std::string& s1, const std::string& s2, int opt);
@ -181,7 +192,7 @@ class SuggestMgr {
void lcs(const char* s, const char* s2, int* l1, int* l2, char** result);
int lcslen(const char* s, const char* s2);
int lcslen(const std::string& s, const std::string& s2);
std::string suggest_hentry_gen(hentry* rv, const char* pattern);
char* suggest_hentry_gen(hentry* rv, const char* pattern);
};
#endif

View File

@ -38,10 +38,8 @@
*
* ***** END LICENSE BLOCK ***** */
#ifndef W_CHAR_HXX_
#define W_CHAR_HXX_
#include <string>
#ifndef __WCHARHXX__
#define __WCHARHXX__
#ifndef GCC
struct w_char {
@ -68,8 +66,10 @@ struct __attribute__((packed)) w_char {
// two character arrays
struct replentry {
std::string pattern;
std::string outstrings[4]; // med, ini, fin, isol
char* pattern;
char* pattern2;
bool start;
bool end;
};
#endif

View File

@ -5,7 +5,7 @@
# file, You can obtain one at http://mozilla.org/MPL/2.0/.
include('/ipc/chromium/chromium-config.mozbuild')
UNIFIED_SOURCES += [
SOURCES += [
'mozEnglishWordUtils.cpp',
'mozInlineSpellChecker.cpp',
'mozInlineSpellWordUtil.cpp',

View File

@ -7,11 +7,12 @@
#ifndef mozilla_gfx_SFNTNameTable_h
#define mozilla_gfx_SFNTNameTable_h
#include "mozilla/Function.h"
#include "mozilla/UniquePtr.h"
#include "mozilla/Vector.h"
#include "u16string.h"
#include <functional>
namespace mozilla {
namespace gfx {
@ -19,7 +20,7 @@ struct NameHeader;
struct NameRecord;
enum ENameDecoder : int;
typedef Vector<function<ENameDecoder(const NameRecord*)>> NameRecordMatchers;
typedef Vector<std::function<ENameDecoder(const NameRecord*)>> NameRecordMatchers;
class SFNTNameTable final
{

View File

@ -6,10 +6,10 @@
#ifndef mozilla_gfx_config_gfxConfig_h
#define mozilla_gfx_config_gfxConfig_h
#include <functional>
#include "gfxFeature.h"
#include "gfxFallback.h"
#include "mozilla/Assertions.h"
#include "mozilla/Function.h"
namespace mozilla {
namespace gfx {
@ -168,13 +168,13 @@ public:
static void EnableFallback(Fallback aFallback, const char* aMessage);
// Run a callback for each initialized FeatureState.
typedef mozilla::function<void(const char* aName,
const char* aDescription,
FeatureState& aFeature)> FeatureIterCallback;
typedef std::function<void(const char* aName,
const char* aDescription,
FeatureState& aFeature)> FeatureIterCallback;
static void ForEachFeature(const FeatureIterCallback& aCallback);
// Run a callback for each enabled fallback.
typedef mozilla::function<void(const char* aName, const char* aMsg)>
typedef std::function<void(const char* aName, const char* aMsg)>
FallbackIterCallback;
static void ForEachFallback(const FallbackIterCallback& aCallback);

View File

@ -6,10 +6,10 @@
#ifndef mozilla_gfx_config_gfxFeature_h
#define mozilla_gfx_config_gfxFeature_h
#include <functional>
#include <stdint.h>
#include "gfxTelemetry.h"
#include "mozilla/Assertions.h"
#include "mozilla/Function.h"
#include "nsString.h"
namespace mozilla {
@ -64,9 +64,9 @@ class FeatureState
// aType is "base", "user", "env", or "runtime".
// aMessage may be null.
typedef mozilla::function<void(const char* aType,
FeatureStatus aStatus,
const char* aMessage)> StatusIterCallback;
typedef std::function<void(const char* aType,
FeatureStatus aStatus,
const char* aMessage)> StatusIterCallback;
void ForEachStatusChange(const StatusIterCallback& aCallback) const;
const char* GetFailureMessage() const;

View File

@ -157,6 +157,8 @@ static const char* const sExtensionNames[] = {
"GL_IMG_texture_compression_pvrtc",
"GL_IMG_texture_npot",
"GL_KHR_debug",
"GL_KHR_texture_compression_astc_hdr",
"GL_KHR_texture_compression_astc_ldr",
"GL_NV_draw_instanced",
"GL_NV_fence",
"GL_NV_framebuffer_blit",

View File

@ -480,6 +480,8 @@ public:
IMG_texture_compression_pvrtc,
IMG_texture_npot,
KHR_debug,
KHR_texture_compression_astc_hdr,
KHR_texture_compression_astc_ldr,
NV_draw_instanced,
NV_fence,
NV_framebuffer_blit,

View File

@ -7,7 +7,6 @@
#ifndef _include_mozilla_gfx_ipc_GPUProcessHost_h_
#define _include_mozilla_gfx_ipc_GPUProcessHost_h_
#include "mozilla/Function.h"
#include "mozilla/Maybe.h"
#include "mozilla/UniquePtr.h"
#include "mozilla/ipc/GeckoChildProcessHost.h"

View File

@ -9,10 +9,11 @@
#include "FrameMetrics.h"
#include "InputData.h"
#include "mozilla/EventForwards.h"
#include "mozilla/Function.h"
#include "mozilla/layers/APZUtils.h"
#include "nsIDOMWindowUtils.h"
#include <functional>
class nsIContent;
class nsIDocument;
class nsIPresShell;
@ -24,7 +25,7 @@ template<class T> class nsCOMPtr;
namespace mozilla {
namespace layers {
typedef function<void(uint64_t, const nsTArray<TouchBehaviorFlags>&)>
typedef std::function<void(uint64_t, const nsTArray<TouchBehaviorFlags>&)>
SetAllowedTouchBehaviorCallback;
/* This class contains some helper methods that facilitate implementing the

View File

@ -11,13 +11,14 @@
#include "FrameMetrics.h" // for ScrollableLayerGuid
#include "Units.h"
#include "mozilla/EventForwards.h"
#include "mozilla/Function.h"
#include "mozilla/layers/GeckoContentController.h" // for APZStateChange
#include "mozilla/RefPtr.h"
#include "nsCOMPtr.h"
#include "nsISupportsImpl.h" // for NS_INLINE_DECL_REFCOUNTING
#include "nsIWeakReferenceUtils.h" // for nsWeakPtr
#include <functional>
template <class> class nsCOMPtr;
class nsIDocument;
class nsIPresShell;
@ -28,9 +29,9 @@ namespace layers {
class ActiveElementManager;
typedef function<void(const ScrollableLayerGuid&,
uint64_t /* input block id */,
bool /* prevent default */)>
typedef std::function<void(const ScrollableLayerGuid&,
uint64_t /* input block id */,
bool /* prevent default */)>
ContentReceivedInputBlockCallback;
/**

Some files were not shown because too many files have changed in this diff Show More