0001
0002
0003
0004
0005
0006
0007
0008
0009
0010
0011
0012
0013
0014
0015
0016
0017
0018
0019
0020
0021
0022
0023
0024
0025
0026
0027
0028 #include <drm/drm_device.h>
0029 #include <drm/via_drm.h>
0030
0031 #include "via_drv.h"
0032
0033 void via_init_futex(drm_via_private_t *dev_priv)
0034 {
0035 unsigned int i;
0036
0037 DRM_DEBUG("\n");
0038
0039 for (i = 0; i < VIA_NR_XVMC_LOCKS; ++i) {
0040 init_waitqueue_head(&(dev_priv->decoder_queue[i]));
0041 XVMCLOCKPTR(dev_priv->sarea_priv, i)->lock = 0;
0042 }
0043 }
0044
0045 void via_cleanup_futex(drm_via_private_t *dev_priv)
0046 {
0047 }
0048
0049 void via_release_futex(drm_via_private_t *dev_priv, int context)
0050 {
0051 unsigned int i;
0052 volatile int *lock;
0053
0054 if (!dev_priv->sarea_priv)
0055 return;
0056
0057 for (i = 0; i < VIA_NR_XVMC_LOCKS; ++i) {
0058 lock = (volatile int *)XVMCLOCKPTR(dev_priv->sarea_priv, i);
0059 if ((_DRM_LOCKING_CONTEXT(*lock) == context)) {
0060 if (_DRM_LOCK_IS_HELD(*lock)
0061 && (*lock & _DRM_LOCK_CONT)) {
0062 wake_up(&(dev_priv->decoder_queue[i]));
0063 }
0064 *lock = 0;
0065 }
0066 }
0067 }
0068
0069 int via_decoder_futex(struct drm_device *dev, void *data, struct drm_file *file_priv)
0070 {
0071 drm_via_futex_t *fx = data;
0072 volatile int *lock;
0073 drm_via_private_t *dev_priv = (drm_via_private_t *) dev->dev_private;
0074 drm_via_sarea_t *sAPriv = dev_priv->sarea_priv;
0075 int ret = 0;
0076
0077 DRM_DEBUG("\n");
0078
0079 if (fx->lock >= VIA_NR_XVMC_LOCKS)
0080 return -EFAULT;
0081
0082 lock = (volatile int *)XVMCLOCKPTR(sAPriv, fx->lock);
0083
0084 switch (fx->func) {
0085 case VIA_FUTEX_WAIT:
0086 VIA_WAIT_ON(ret, dev_priv->decoder_queue[fx->lock],
0087 (fx->ms / 10) * (HZ / 100), *lock != fx->val);
0088 return ret;
0089 case VIA_FUTEX_WAKE:
0090 wake_up(&(dev_priv->decoder_queue[fx->lock]));
0091 return 0;
0092 }
0093 return 0;
0094 }