Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Contribute to GitLab
Sign in / Register
Toggle navigation
F
ffmpeg.wasm-core
Project
Project
Details
Activity
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
Linshizhi
ffmpeg.wasm-core
Commits
9628e5a4
Commit
9628e5a4
authored
Mar 09, 2013
by
Ronald S. Bultje
Committed by
Michael Niedermayer
Mar 13, 2013
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
hpeldsp: add half-pel functions (currently copies of dsputil).
parent
1f27053b
Hide whitespace changes
Inline
Side-by-side
Showing
7 changed files
with
434 additions
and
6 deletions
+434
-6
configure
configure
+1
-0
Makefile
libavcodec/Makefile
+1
-0
dsputil.h
libavcodec/dsputil.h
+1
-6
hpeldsp.c
libavcodec/hpeldsp.c
+65
-0
hpeldsp.h
libavcodec/hpeldsp.h
+105
-0
hpeldsp_template.c
libavcodec/hpeldsp_template.c
+254
-0
rnd_avg.h
libavcodec/rnd_avg.h
+7
-0
No files found.
configure
View file @
9628e5a4
...
...
@@ -1518,6 +1518,7 @@ CONFIG_EXTRA="
h264dsp
h264pred
h264qpel
hpeldsp
huffman
lgplv3
lpc
...
...
libavcodec/Makefile
View file @
9628e5a4
...
...
@@ -49,6 +49,7 @@ OBJS-$(CONFIG_H264CHROMA) += h264chroma.o
OBJS-$(CONFIG_H264DSP)
+=
h264dsp.o
h264idct.o
OBJS-$(CONFIG_H264PRED)
+=
h264pred.o
OBJS-$(CONFIG_H264QPEL)
+=
h264qpel.o
OBJS-$(CONFIG_HPELDSP)
+=
hpeldsp.o
OBJS-$(CONFIG_HUFFMAN)
+=
huffman.o
OBJS-$(CONFIG_LIBXVID)
+=
libxvid_rc.o
OBJS-$(CONFIG_LPC)
+=
lpc.o
...
...
libavcodec/dsputil.h
View file @
9628e5a4
...
...
@@ -32,6 +32,7 @@
#include "libavutil/intreadwrite.h"
#include "avcodec.h"
#include "rnd_avg.h"
//#define DEBUG
...
...
@@ -103,12 +104,6 @@ DEF_OLD_QPEL(qpel8_mc32_old_c)
DEF_OLD_QPEL
(
qpel8_mc13_old_c
)
DEF_OLD_QPEL
(
qpel8_mc33_old_c
)
#define CALL_2X_PIXELS(a, b, n)\
static void a(uint8_t *block, const uint8_t *pixels, ptrdiff_t line_size, int h){\
b(block , pixels , line_size, h);\
b(block+n, pixels+n, line_size, h);\
}
/* motion estimation */
// h is limited to {width/2, width, 2*width} but never larger than 16 and never smaller than 2
// although currently h<4 is not used as functions with width <8 are neither used nor implemented
...
...
libavcodec/hpeldsp.c
0 → 100644
View file @
9628e5a4
/*
* Half-pel DSP functions.
* Copyright (c) 2000, 2001 Fabrice Bellard
* Copyright (c) 2002-2004 Michael Niedermayer <michaelni@gmx.at>
*
* gmc & q-pel & 32/64 bit based MC by Michael Niedermayer <michaelni@gmx.at>
*
* This file is part of FFmpeg.
*
* FFmpeg is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* FFmpeg is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with FFmpeg; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*/
/**
* @file
* Half-pel DSP functions.
*/
#include "libavutil/attributes.h"
#include "hpeldsp.h"
#define BIT_DEPTH 8
#include "hpeldsp_template.c"
av_cold
void
ff_hpeldsp_init
(
HpelDSPContext
*
c
,
int
flags
)
{
#define hpel_funcs(prefix, idx, num) \
c->prefix ## _pixels_tab idx [0] = prefix ## _pixels ## num ## _8_c; \
c->prefix ## _pixels_tab idx [1] = prefix ## _pixels ## num ## _x2_8_c; \
c->prefix ## _pixels_tab idx [2] = prefix ## _pixels ## num ## _y2_8_c; \
c->prefix ## _pixels_tab idx [3] = prefix ## _pixels ## num ## _xy2_8_c
hpel_funcs
(
put
,
[
0
],
16
);
hpel_funcs
(
put
,
[
1
],
8
);
hpel_funcs
(
put
,
[
2
],
4
);
hpel_funcs
(
put
,
[
3
],
2
);
hpel_funcs
(
put_no_rnd
,
[
0
],
16
);
hpel_funcs
(
put_no_rnd
,
[
1
],
8
);
hpel_funcs
(
avg
,
[
0
],
16
);
hpel_funcs
(
avg
,
[
1
],
8
);
hpel_funcs
(
avg
,
[
2
],
4
);
hpel_funcs
(
avg
,
[
3
],
2
);
hpel_funcs
(
avg_no_rnd
,,
16
);
#if 0
if (ARCH_X86) ff_hpeldsp_init_x86 (c, flags);
if (ARCH_ARM) ff_hpeldsp_init_arm (c, flags);
if (HAVE_VIS) ff_hpeldsp_init_vis (c, flags);
if (ARCH_ALPHA) ff_hpeldsp_init_alpha (c, flags);
if (ARCH_PPC) ff_hpeldsp_init_ppc (c, flags);
if (ARCH_SH4) ff_hpeldsp_init_sh4 (c, flags);
if (ARCH_BFIN) ff_hpeldsp_init_bfin (c, flags);
#endif
}
libavcodec/hpeldsp.h
0 → 100644
View file @
9628e5a4
/*
* Half-pel DSP functions.
* Copyright (c) 2000, 2001, 2002 Fabrice Bellard
* Copyright (c) 2002-2004 Michael Niedermayer <michaelni@gmx.at>
*
* This file is part of FFmpeg.
*
* FFmpeg is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* FFmpeg is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with FFmpeg; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*/
/**
* @file
* Half-pel DSP functions.
*/
#ifndef AVCODEC_HPELDSP_H
#define AVCODEC_HPELDSP_H
#include <stdint.h>
#include <stddef.h>
/* add and put pixel (decoding) */
// blocksizes for op_pixels_func are 8x4,8x8 16x8 16x16
// h for op_pixels_func is limited to {width/2, width} but never larger
// than 16 and never smaller than 4
typedef
void
(
*
hpel_pixels_func
)(
uint8_t
*
block
/*align width (8 or 16)*/
,
const
uint8_t
*
pixels
/*align 1*/
,
ptrdiff_t
line_size
,
int
h
);
/**
* Half-pel DSP context.
*/
typedef
struct
HpelDSPContext
{
/**
* Halfpel motion compensation with rounding (a+b+1)>>1.
* this is an array[4][4] of motion compensation functions for 4
* horizontal blocksizes (8,16) and the 4 halfpel positions<br>
* *pixels_tab[ 0->16xH 1->8xH ][ xhalfpel + 2*yhalfpel ]
* @param block destination where the result is stored
* @param pixels source
* @param line_size number of bytes in a horizontal line of block
* @param h height
*/
hpel_pixels_func
put_pixels_tab
[
4
][
4
];
/**
* Halfpel motion compensation with rounding (a+b+1)>>1.
* This is an array[4][4] of motion compensation functions for 4
* horizontal blocksizes (8,16) and the 4 halfpel positions<br>
* *pixels_tab[ 0->16xH 1->8xH ][ xhalfpel + 2*yhalfpel ]
* @param block destination into which the result is averaged (a+b+1)>>1
* @param pixels source
* @param line_size number of bytes in a horizontal line of block
* @param h height
*/
hpel_pixels_func
avg_pixels_tab
[
4
][
4
];
/**
* Halfpel motion compensation with no rounding (a+b)>>1.
* this is an array[2][4] of motion compensation functions for 2
* horizontal blocksizes (8,16) and the 4 halfpel positions<br>
* *pixels_tab[ 0->16xH 1->8xH ][ xhalfpel + 2*yhalfpel ]
* @param block destination where the result is stored
* @param pixels source
* @param line_size number of bytes in a horizontal line of block
* @param h height
*/
hpel_pixels_func
put_no_rnd_pixels_tab
[
2
][
4
];
/**
* Halfpel motion compensation with no rounding (a+b)>>1.
* this is an array[4] of motion compensation functions for 1
* horizontal blocksize (16) and the 4 halfpel positions<br>
* *pixels_tab[0][ xhalfpel + 2*yhalfpel ]
* @param block destination into which the result is averaged (a+b)>>1
* @param pixels source
* @param line_size number of bytes in a horizontal line of block
* @param h height
*/
hpel_pixels_func
avg_no_rnd_pixels_tab
[
4
];
}
HpelDSPContext
;
void
ff_hpeldsp_init
(
HpelDSPContext
*
p
,
int
flags
);
void
ff_hpeldsp_init_alpha
(
HpelDSPContext
*
c
,
int
flags
);
void
ff_hpeldsp_init_arm
(
HpelDSPContext
*
c
,
int
flags
);
void
ff_hpeldsp_init_bfin
(
HpelDSPContext
*
c
,
int
flags
);
void
ff_hpeldsp_init_x86
(
HpelDSPContext
*
c
,
int
flags
);
void
ff_hpeldsp_init_ppc
(
HpelDSPContext
*
c
,
int
flags
);
void
ff_hpeldsp_init_sh4
(
HpelDSPContext
*
c
,
int
flags
);
void
ff_hpeldsp_init_vis
(
HpelDSPContext
*
c
,
int
flags
);
#endif
/* AVCODEC_HPELDSP_H */
libavcodec/hpeldsp_template.c
0 → 100644
View file @
9628e5a4
/*
* Half-pel DSP functions.
* Copyright (c) 2000, 2001 Fabrice Bellard
* Copyright (c) 2002-2004 Michael Niedermayer <michaelni@gmx.at>
*
* gmc & q-pel & 32/64 bit based MC by Michael Niedermayer <michaelni@gmx.at>
*
* This file is part of FFmpeg.
*
* FFmpeg is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* FFmpeg is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with FFmpeg; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*/
/**
* @file
* Half-pel DSP functions.
*/
#include "bit_depth_template.c"
#include "hpel_template.c"
#define PIXOP2(OPNAME, OP) \
static inline void FUNC(OPNAME ## _no_rnd_pixels8_l2)(uint8_t *dst, const uint8_t *src1, const uint8_t *src2, int dst_stride, \
int src_stride1, int src_stride2, int h){\
int i;\
for(i=0; i<h; i++){\
pixel4 a,b;\
a= AV_RN4P(&src1[i*src_stride1 ]);\
b= AV_RN4P(&src2[i*src_stride2 ]);\
OP(*((pixel4*)&dst[i*dst_stride ]), no_rnd_avg_pixel4(a, b));\
a= AV_RN4P(&src1[i*src_stride1+4*sizeof(pixel)]);\
b= AV_RN4P(&src2[i*src_stride2+4*sizeof(pixel)]);\
OP(*((pixel4*)&dst[i*dst_stride+4*sizeof(pixel)]), no_rnd_avg_pixel4(a, b));\
}\
}\
\
static inline void FUNCC(OPNAME ## _no_rnd_pixels8_x2)(uint8_t *block, const uint8_t *pixels, ptrdiff_t line_size, int h){\
FUNC(OPNAME ## _no_rnd_pixels8_l2)(block, pixels, pixels+sizeof(pixel), line_size, line_size, line_size, h);\
}\
\
static inline void FUNCC(OPNAME ## _pixels8_x2)(uint8_t *block, const uint8_t *pixels, ptrdiff_t line_size, int h){\
FUNC(OPNAME ## _pixels8_l2)(block, pixels, pixels+sizeof(pixel), line_size, line_size, line_size, h);\
}\
\
static inline void FUNCC(OPNAME ## _no_rnd_pixels8_y2)(uint8_t *block, const uint8_t *pixels, ptrdiff_t line_size, int h){\
FUNC(OPNAME ## _no_rnd_pixels8_l2)(block, pixels, pixels+line_size, line_size, line_size, line_size, h);\
}\
\
static inline void FUNCC(OPNAME ## _pixels8_y2)(uint8_t *block, const uint8_t *pixels, ptrdiff_t line_size, int h){\
FUNC(OPNAME ## _pixels8_l2)(block, pixels, pixels+line_size, line_size, line_size, line_size, h);\
}\
\
static inline void FUNCC(OPNAME ## _pixels4_x2)(uint8_t *block, const uint8_t *pixels, ptrdiff_t line_size, int h){\
FUNC(OPNAME ## _pixels4_l2)(block, pixels, pixels+sizeof(pixel), line_size, line_size, line_size, h);\
}\
\
static inline void FUNCC(OPNAME ## _pixels4_y2)(uint8_t *block, const uint8_t *pixels, ptrdiff_t line_size, int h){\
FUNC(OPNAME ## _pixels4_l2)(block, pixels, pixels+line_size, line_size, line_size, line_size, h);\
}\
\
static inline void FUNCC(OPNAME ## _pixels2_x2)(uint8_t *block, const uint8_t *pixels, ptrdiff_t line_size, int h){\
FUNC(OPNAME ## _pixels2_l2)(block, pixels, pixels+sizeof(pixel), line_size, line_size, line_size, h);\
}\
\
static inline void FUNCC(OPNAME ## _pixels2_y2)(uint8_t *block, const uint8_t *pixels, ptrdiff_t line_size, int h){\
FUNC(OPNAME ## _pixels2_l2)(block, pixels, pixels+line_size, line_size, line_size, line_size, h);\
}\
\
static inline void FUNCC(OPNAME ## _pixels2_xy2)(uint8_t *_block, const uint8_t *_pixels, ptrdiff_t line_size, int h)\
{\
int i, a0, b0, a1, b1;\
pixel *block = (pixel*)_block;\
const pixel *pixels = (const pixel*)_pixels;\
line_size >>= sizeof(pixel)-1;\
a0= pixels[0];\
b0= pixels[1] + 2;\
a0 += b0;\
b0 += pixels[2];\
\
pixels+=line_size;\
for(i=0; i<h; i+=2){\
a1= pixels[0];\
b1= pixels[1];\
a1 += b1;\
b1 += pixels[2];\
\
block[0]= (a1+a0)>>2;
/* FIXME non put */
\
block[1]= (b1+b0)>>2;\
\
pixels+=line_size;\
block +=line_size;\
\
a0= pixels[0];\
b0= pixels[1] + 2;\
a0 += b0;\
b0 += pixels[2];\
\
block[0]= (a1+a0)>>2;\
block[1]= (b1+b0)>>2;\
pixels+=line_size;\
block +=line_size;\
}\
}\
\
static inline void FUNCC(OPNAME ## _pixels4_xy2)(uint8_t *block, const uint8_t *pixels, ptrdiff_t line_size, int h)\
{\
/* FIXME HIGH BIT DEPTH */
\
int i;\
const uint32_t a= AV_RN32(pixels );\
const uint32_t b= AV_RN32(pixels+1);\
uint32_t l0= (a&0x03030303UL)\
+ (b&0x03030303UL)\
+ 0x02020202UL;\
uint32_t h0= ((a&0xFCFCFCFCUL)>>2)\
+ ((b&0xFCFCFCFCUL)>>2);\
uint32_t l1,h1;\
\
pixels+=line_size;\
for(i=0; i<h; i+=2){\
uint32_t a= AV_RN32(pixels );\
uint32_t b= AV_RN32(pixels+1);\
l1= (a&0x03030303UL)\
+ (b&0x03030303UL);\
h1= ((a&0xFCFCFCFCUL)>>2)\
+ ((b&0xFCFCFCFCUL)>>2);\
OP(*((uint32_t*)block), h0+h1+(((l0+l1)>>2)&0x0F0F0F0FUL));\
pixels+=line_size;\
block +=line_size;\
a= AV_RN32(pixels );\
b= AV_RN32(pixels+1);\
l0= (a&0x03030303UL)\
+ (b&0x03030303UL)\
+ 0x02020202UL;\
h0= ((a&0xFCFCFCFCUL)>>2)\
+ ((b&0xFCFCFCFCUL)>>2);\
OP(*((uint32_t*)block), h0+h1+(((l0+l1)>>2)&0x0F0F0F0FUL));\
pixels+=line_size;\
block +=line_size;\
}\
}\
\
static inline void FUNCC(OPNAME ## _pixels8_xy2)(uint8_t *block, const uint8_t *pixels, ptrdiff_t line_size, int h)\
{\
/* FIXME HIGH BIT DEPTH */
\
int j;\
for(j=0; j<2; j++){\
int i;\
const uint32_t a= AV_RN32(pixels );\
const uint32_t b= AV_RN32(pixels+1);\
uint32_t l0= (a&0x03030303UL)\
+ (b&0x03030303UL)\
+ 0x02020202UL;\
uint32_t h0= ((a&0xFCFCFCFCUL)>>2)\
+ ((b&0xFCFCFCFCUL)>>2);\
uint32_t l1,h1;\
\
pixels+=line_size;\
for(i=0; i<h; i+=2){\
uint32_t a= AV_RN32(pixels );\
uint32_t b= AV_RN32(pixels+1);\
l1= (a&0x03030303UL)\
+ (b&0x03030303UL);\
h1= ((a&0xFCFCFCFCUL)>>2)\
+ ((b&0xFCFCFCFCUL)>>2);\
OP(*((uint32_t*)block), h0+h1+(((l0+l1)>>2)&0x0F0F0F0FUL));\
pixels+=line_size;\
block +=line_size;\
a= AV_RN32(pixels );\
b= AV_RN32(pixels+1);\
l0= (a&0x03030303UL)\
+ (b&0x03030303UL)\
+ 0x02020202UL;\
h0= ((a&0xFCFCFCFCUL)>>2)\
+ ((b&0xFCFCFCFCUL)>>2);\
OP(*((uint32_t*)block), h0+h1+(((l0+l1)>>2)&0x0F0F0F0FUL));\
pixels+=line_size;\
block +=line_size;\
}\
pixels+=4-line_size*(h+1);\
block +=4-line_size*h;\
}\
}\
\
static inline void FUNCC(OPNAME ## _no_rnd_pixels8_xy2)(uint8_t *block, const uint8_t *pixels, ptrdiff_t line_size, int h)\
{\
/* FIXME HIGH BIT DEPTH */
\
int j;\
for(j=0; j<2; j++){\
int i;\
const uint32_t a= AV_RN32(pixels );\
const uint32_t b= AV_RN32(pixels+1);\
uint32_t l0= (a&0x03030303UL)\
+ (b&0x03030303UL)\
+ 0x01010101UL;\
uint32_t h0= ((a&0xFCFCFCFCUL)>>2)\
+ ((b&0xFCFCFCFCUL)>>2);\
uint32_t l1,h1;\
\
pixels+=line_size;\
for(i=0; i<h; i+=2){\
uint32_t a= AV_RN32(pixels );\
uint32_t b= AV_RN32(pixels+1);\
l1= (a&0x03030303UL)\
+ (b&0x03030303UL);\
h1= ((a&0xFCFCFCFCUL)>>2)\
+ ((b&0xFCFCFCFCUL)>>2);\
OP(*((uint32_t*)block), h0+h1+(((l0+l1)>>2)&0x0F0F0F0FUL));\
pixels+=line_size;\
block +=line_size;\
a= AV_RN32(pixels );\
b= AV_RN32(pixels+1);\
l0= (a&0x03030303UL)\
+ (b&0x03030303UL)\
+ 0x01010101UL;\
h0= ((a&0xFCFCFCFCUL)>>2)\
+ ((b&0xFCFCFCFCUL)>>2);\
OP(*((uint32_t*)block), h0+h1+(((l0+l1)>>2)&0x0F0F0F0FUL));\
pixels+=line_size;\
block +=line_size;\
}\
pixels+=4-line_size*(h+1);\
block +=4-line_size*h;\
}\
}\
\
CALL_2X_PIXELS(FUNCC(OPNAME ## _pixels16_x2) , FUNCC(OPNAME ## _pixels8_x2) , 8*sizeof(pixel))\
CALL_2X_PIXELS(FUNCC(OPNAME ## _pixels16_y2) , FUNCC(OPNAME ## _pixels8_y2) , 8*sizeof(pixel))\
CALL_2X_PIXELS(FUNCC(OPNAME ## _pixels16_xy2), FUNCC(OPNAME ## _pixels8_xy2), 8*sizeof(pixel))\
av_unused CALL_2X_PIXELS(FUNCC(OPNAME ## _no_rnd_pixels16) , FUNCC(OPNAME ## _pixels8) , 8*sizeof(pixel))\
CALL_2X_PIXELS(FUNCC(OPNAME ## _no_rnd_pixels16_x2) , FUNCC(OPNAME ## _no_rnd_pixels8_x2) , 8*sizeof(pixel))\
CALL_2X_PIXELS(FUNCC(OPNAME ## _no_rnd_pixels16_y2) , FUNCC(OPNAME ## _no_rnd_pixels8_y2) , 8*sizeof(pixel))\
CALL_2X_PIXELS(FUNCC(OPNAME ## _no_rnd_pixels16_xy2), FUNCC(OPNAME ## _no_rnd_pixels8_xy2), 8*sizeof(pixel))\
#define op_avg(a, b) a = rnd_avg_pixel4(a, b)
#define op_put(a, b) a = b
#if BIT_DEPTH == 8
#define put_no_rnd_pixels8_8_c put_pixels8_8_c
PIXOP2
(
avg
,
op_avg
)
PIXOP2
(
put
,
op_put
)
#endif
#undef op_avg
#undef op_put
libavcodec/rnd_avg.h
View file @
9628e5a4
...
...
@@ -22,8 +22,15 @@
#ifndef AVCODEC_RND_AVG_H
#define AVCODEC_RND_AVG_H
#include <stddef.h>
#include <stdint.h>
#define CALL_2X_PIXELS(a, b, n)\
static void a(uint8_t *block, const uint8_t *pixels, ptrdiff_t line_size, int h){\
b(block , pixels , line_size, h);\
b(block+n, pixels+n, line_size, h);\
}
#define BYTE_VEC32(c) ((c)*0x01010101UL)
#define BYTE_VEC64(c) ((c)*0x0001000100010001UL)
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment