Back to home page

LXR

 
 

    


File indexing completed on 2025-05-11 08:24:32

0001 /* SPDX-License-Identifier: BSD-2-Clause */
0002 
0003 /*! @file
0004  * @brief Check how rtems_bdbuf_read() handles two readers waiting
0005  * for a buffer with the same block number in cases when disk device
0006  * driver reports success in read complete notification.
0007  *
0008  * Test sequence:
0009  * -# Call rtems_bdbuf_read() function in thread #1 and block on
0010  *    waiting for read complete notification.
0011  * -# Call rtems_bdbuf_read() function in thread #2 for the same
0012  *    block number. As the result it blocks on this read as well
0013  *    (but it will block on transfer semaphore).
0014  * -# Disk device reports success in read complete notification.
0015  *    As the result rtems_bdbuf_read() function returns RTEMS_SUCCESSFUL
0016  *    in thread #1.
0017  * -# Thread #1 releases buffer with rtems_bdbuf_release() function.
0018  * -# rtems_bdbuf_read() function in thread #2 unlocks and
0019  *    returns RTEMS_SUCCESSFUL.
0020  * -# Call rtems_bdbuf_release() function in thread #2.
0021  * .
0022  *
0023  * Copyright (C) 2010 OKTET Labs, St.-Petersburg, Russia
0024  * Author: Oleg Kravtsov <Oleg.Kravtsov@oktetlabs.ru>
0025  *
0026  * Redistribution and use in source and binary forms, with or without
0027  * modification, are permitted provided that the following conditions
0028  * are met:
0029  * 1. Redistributions of source code must retain the above copyright
0030  *    notice, this list of conditions and the following disclaimer.
0031  * 2. Redistributions in binary form must reproduce the above copyright
0032  *    notice, this list of conditions and the following disclaimer in the
0033  *    documentation and/or other materials provided with the distribution.
0034  *
0035  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
0036  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
0037  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
0038  * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
0039  * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
0040  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
0041  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
0042  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
0043  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
0044  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
0045  * POSSIBILITY OF SUCH DAMAGE.
0046  */
0047 
0048 #ifdef HAVE_CONFIG_H
0049 #include "config.h"
0050 #endif
0051 
0052 #include "bdbuf_tests.h"
0053 
0054 static rtems_task bdbuf_test1_4_thread1(rtems_task_argument arg);
0055 static rtems_task bdbuf_test1_4_thread2(rtems_task_argument arg);
0056 
0057 /* Block number used in the test */
0058 #define TEST_BLK_NUM 40
0059 
0060 void
0061 bdbuf_test1_4_main()
0062 {
0063     bdbuf_test_msg msg;
0064 
0065     TEST_START("Test 1.4");
0066 
0067     START_THREAD(1, bdbuf_test1_4_thread1);
0068     START_THREAD(2, bdbuf_test1_4_thread2);
0069 
0070     /*
0071      * Step 1:
0072      * Thread #1 calls rtems_bdbuf_read() and we block
0073      * this thread on data transfer operation.
0074      */
0075     WAIT_DRV_MSG(&msg);
0076 
0077     /*
0078      * Step 2:
0079      * Thread #2 calls rtems_bdbuf_read() for the same
0080      * block number, as the result it shall block waiting
0081      * on buffer state change (waiting on TRANSFER state).
0082      */
0083     CONTINUE_THREAD(2);
0084 
0085     /* Make sure threads #1 and #2 managed blocked on the buffer. */
0086     CHECK_THREAD_BLOCKED(1);
0087     CHECK_THREAD_BLOCKED(2);
0088 
0089     /*
0090      * Step 3:
0091      * Unblock thread #1 by reporting successful data transfer result.
0092      */
0093     SEND_DRV_MSG(0, 0, RTEMS_SUCCESSFUL, 0);
0094 
0095     /*
0096      * Wait for sync from thread #1.
0097      */
0098     WAIT_THREAD_SYNC(1);
0099     TEST_CHECK_RESULT("3");
0100 
0101     /*
0102      * Check that thread #2 is still blocked.
0103      */
0104     CHECK_THREAD_BLOCKED(2);
0105 
0106     /*
0107      * Step 4:
0108      * Thread #1 releases buffer with bdbuf_release() call.
0109      */
0110     CONTINUE_THREAD(1);
0111 
0112     /*
0113      * Step 5:
0114      * On buffer release operation, we should have unblock
0115      * of thread #2 that is wating on read buffer operation.
0116      */
0117     WAIT_THREAD_SYNC(2);
0118     TEST_CHECK_RESULT("5");
0119 
0120     /*
0121      * Step 6:
0122      * Thread #2 release buffer.
0123      */
0124     CONTINUE_THREAD(2);
0125 
0126     TEST_STOP();
0127 }
0128 
0129 static rtems_task
0130 bdbuf_test1_4_thread1(rtems_task_argument arg)
0131 {
0132     rtems_status_code   rc;
0133     rtems_bdbuf_buffer *bd = NULL;
0134 
0135     /*
0136      * Step 1 - 3:
0137      * Try to read blk #N on thread #1
0138      * We will block on this read and meanwhile
0139      * thread #2 will try to read the same block.
0140      * After blocking on read in thread #2, device
0141      * driver will notify successful completion of
0142      * date transfer, and as the result this call
0143      * will return valid buffer.
0144      */
0145     rc = rtems_bdbuf_read(test_dd, TEST_BLK_NUM, &bd);
0146     if (rc != RTEMS_SUCCESSFUL)
0147     {
0148         TEST_FAILED();
0149     }
0150     CONTINUE_MAIN(1);
0151 
0152     /*
0153      * Step 4:
0154      * Release buffer returned on the previous step.
0155      */
0156     rc = rtems_bdbuf_release(bd);
0157     if (rc != RTEMS_SUCCESSFUL)
0158     {
0159         TEST_FAILED();
0160     }
0161     THREAD_END();
0162 }
0163 
0164 static rtems_task
0165 bdbuf_test1_4_thread2(rtems_task_argument arg)
0166 {
0167     rtems_status_code   rc;
0168     rtems_bdbuf_buffer *bd = NULL;
0169 
0170     WAIT_MAIN_SYNC(2);
0171 
0172     /*
0173      * Step 2:
0174      * Try to read block #N. Right now thread #1 is waiting
0175      * on data transfer operation, so we will block here as well.
0176      *
0177      * Step 5:
0178      * On step 4 thread #1 releases buffer and as the result
0179      * our read operation should finish with success.
0180      */
0181     rc = rtems_bdbuf_read(test_dd, TEST_BLK_NUM, &bd);
0182     if (rc != RTEMS_SUCCESSFUL)
0183     {
0184         TEST_FAILED();
0185     }
0186     CONTINUE_MAIN(2);
0187 
0188     /*
0189      * Step 6:
0190      * Release buffer returned on the previous step.
0191      */
0192     rc = rtems_bdbuf_release(bd);
0193     if (rc != RTEMS_SUCCESSFUL)
0194     {
0195         TEST_FAILED();
0196     }
0197     THREAD_END();
0198 }