美文网首页并发
synchronzied偏向锁与linux源码调用关系

synchronzied偏向锁与linux源码调用关系

作者: loveFXX | 来源:发表于2019-12-01 21:26 被阅读0次

    示例代码

    public class SyncDemo {
    
        static {
            System.loadLibrary( "MyThreadSyncNative" );
        }
        Object o= new Object();
        public static void main(String[] args) throws InterruptedException {
            System.out.println("-------------------------");
            Thread.sleep(5000);
            SyncDemo syncDemo = new SyncDemo();
            syncDemo.start();
        }
        public void start() {
            Thread thread = new Thread() {
                public void run() {
                    while (true) {
                        try {
                            Thread.sleep(500);
                            sync();
                        } catch (InterruptedException e) {
    
                        }
                    }
                }
            };
    
            Thread thread2 = new Thread() {
                @Override
                public void run() {
                    while (true) {
                        try {
                            Thread.sleep(500);
                            sync();
                        } catch (InterruptedException e) {
                            e.printStackTrace();
                        }
                    }
                }
            };
    
            thread.setName("t1");
    //      thread2.setName("t2");
            thread.start();
    //      thread2.start();
        }
    
    
        public native void  getMytid();
        public  void sync() throws InterruptedException {
            synchronized (o) {
                getMytid();//打印了当前线程的id
            }
        }
    }
    

    对于示例代码分析,使用synchronized关键字。如果thread2线程不执行,持有锁将会是偏向锁。thread2运行将会变成重量级锁。

    synchronized

    synchronized种类:
    1、偏向锁 (方法需要保持线程安全,实际情况不一定有互斥,所以偏向锁是synchronzied锁的对象如果没有资源竞争的情况下存在的。 只会调用一次os函数实现)
    2、轻量级锁
    3、重量级锁(互斥 借助os函数来实现的锁)
    java锁的实现对应操作系统函数(在pthread_mutex_lock.c文件)
    java锁有关的操作系统相关方法
    pthread_mutex_t pthread_mutex_init pthread_mutex_lock pthread_mutex_unlock

    linux编译glibc

    下面编译glibc是在18.04.1-Ubuntu环境


    image.png
    下载glibc

    http://ftp.gnu.org/gnu/glibc/
    首先,查看当前版本(2.27)
    ldd --version

    安装jdk

    apt-get install openjdk-8-jdk

    安装gcc make gawk bison

    apt-get install gcc -y
    apt-get install make gawk bison -y

    下载glibc

    与之前版本相同的
    wget http://ftp.gnu.org/gnu/glibc/glibc-2.27.tar.gz

    解压

    tar zxvf glibc-2.27.tar.gz
    cd glibc-2.27

    修改pthread_mutex_lock.c

    /root/glibc-2.27/nptl/pthread_mutex_lock.c文件
    添加 #include <stdio.h>
    fprintf(stderr,"my message tid=%lu\n",pthread_self());


    image.png
    新建目录

    cd /root/glibc-2.27/
    mkdir myglib
    cd myglib/

    编译

    ../configure --prefix=/usr
    (或编译命令../configure --prefix=/usr --disable-profile --enable-add-ons --with-head=/usr/include --with-binutils=/usr/bin)
    make
    make install

    生成so文件

    示例代码调用了本地方法getMytid,System.loadLibrary( "MyThreadSyncNative" );调用加载系统库。具体步骤可参考【java线程模型】
    由于,我修改了pthread_mutex_lock.c文件。运行java命令


    image.png

    到这里说明glibc编译成功

    证明偏向锁

    证明synchronzied偏向锁只会调用一次操作系统函数
    根据示例代码测试


    image.png

    把示例代码中thread2.start();注释去掉,即两个线程运行


    image.png

    总结:

    java对象持有锁与操作系统锁一一对应关系
    jvm不推荐(stop()方法)停止一个线程,一定要执行完 。使用interrupt方法
    interrupt方法
    1、优雅停止线程,资源能够释放。
    2、能解阻塞,继续往下执行。
    3、可以给isInterrupted赋值

    相关文章

      网友评论

        本文标题:synchronzied偏向锁与linux源码调用关系

        本文链接:https://www.haomeiwen.com/subject/mtytgctx.html